0

Ich bin neu in MongoDB und ich habe gekämpft, um eine bestimmte Abfrage zu erhalten, ohne Glück zu arbeiten. Ich habe eine Sammlung mit Millionen von Dokumenten mit einem Datum und einer Menge, ich möchte die Aggregationen für bestimmte Zeiträume erhalten. Zum Beispiel möchte ich die Zählung erhalten, die Menge Summen für die Zeiträume zwischen 1/1/2015 - 15/1/2015 und zwischen 1/2/2015 - 15/2/2015Gruppe basiert auf diskreten Datumsbereichen

Eine Probe Sammlung

{ "_id" : "148404972864202083547392254", "account" : "3600", "amount" : 50, "date" : ISODate("2017-01-01T12:02:08.642Z")} 

{ "_id" : "148404972864202085437392254", "account" : "3600", "amount" : 50, "date" : ISODate("2017-01-03T12:02:08.642Z")} 

{ "_id" : "148404372864202083547392254", "account" : "3600", "amount" : 70, "date" : ISODate("2017-01-09T12:02:08.642Z")} 

{ "_id" : "148404972864202083547342254", "account" : "3600", "amount" : 150, "date" : ISODate("2017-01-22T12:02:08.642Z")} 

{ "_id" : "148404922864202083547392254", "account" : "3600", "amount" : 200, "date" : ISODate("2017-02-02T12:02:08.642Z")} 

{ "_id" : "148404972155502083547392254", "account" : "3600", "amount" : 30, "date" : ISODate("2017-02-7T12:02:08.642Z")} 

{ "_id" : "148404972864202122254732254", "account" : "3600", "amount" : 10, "date" : ISODate("2017-02-10T12:02:08.642Z")} 

für Zeiträume zwischen 1/1/2017 - 10/10/2017 und 1/2/2017 - 10/2/2017 der Ausgang so sein würde:

  • 1/1/2017 - 2017.10.01 - count = 3, Anzahl Summation: 170
  • 2017.10.02 - 15/2/2017 - Anzahl = 2, Summe Summe: 40

Kann man mit so unterschiedlichen Datumsbereichen arbeiten? Der Code wäre in Java, aber als Beispiel in Mongo, kann mir bitte jemand helfen?

Antwort

1

Es muss eine elegantere Lösung als diese geben. Wie auch immer, Sie können es in eine Funktion einfügen und datumsbezogene Argumente verallgemeinern.

Zuerst müssen Sie eine Projektion machen, die gleichzeitig entscheidet, in welchen Bereich ein Element geht (beachten Sie den großen Ausdruck $switch). Standardmäßig wird ein Element in den 'Null' Bereich gesetzt.

Dann filtern Sie Ergebnisse heraus, die nicht Ihren Kriterien entsprechen (d. H. Bereich! = Null).

Der allerletzte Schritt besteht darin, die Elemente nach dem Bereich zu gruppieren und alle erforderlichen Berechnungen durchzuführen.

db.items.aggregate([ 
    { $project : { 
    amount : true, 
    account : true, 
    date : true, 
    range : { 
     $switch : { 
     branches : [ 
      { 
      case : { 
       $and : [ 
       { $gte : [ "$date", ISODate("2017-01-01T00:00:00.000Z") ] }, 
       { $lt : [ "$date", ISODate("2017-01-10T00:00:00.000Z") ] } 
       ] 
      }, 
      then : { $concat : [ 
       { $dateToString: { format: "%d/%m/%Y", date: ISODate("2017-01-01T00:00:00.000Z") } }, 
       { $literal : " - " }, 
       { $dateToString: { format: "%d/%m/%Y", date: ISODate("2017-01-10T00:00:00.000Z") } } 
      ] } 
      }, 
      { 
      case : { 
       $and : [ 
       { $gte : [ "$date", ISODate("2017-02-01T00:00:00.000Z") ] }, 
       { $lt : [ "$date", ISODate("2017-02-10T00:00:00.000Z") ] } 
       ] 
      }, 
      then : { $concat : [ 
       { $dateToString: { format: "%d/%m/%Y", date: ISODate("2017-02-01T00:00:00.000Z") } }, 
       { $literal : " - " }, 
       { $dateToString: { format: "%d/%m/%Y", date: ISODate("2017-02-10T00:00:00.000Z") } } 
      ] } 
      } 
     ], 
     default : null 
     } 
    } 
    } }, 
    { $match : { range : { $ne : null } } }, 
    { $group : { 
    _id : "$range", 
    count : { $sum : 1 }, 
    "amount summation" : { $sum : "$amount" } 
    } } 
]) 

Basierend auf Ihre Daten werden es die folgenden Ergebnisse liefern *:

{ "_id" : "01/02/2017 - 10/02/2017", "count" : 2, "amount summation" : 230 } 
{ "_id" : "01/01/2017 - 10/01/2017", "count" : 3, "amount summation" : 170 } 

* Ich glaube, dass Sie in Ihren Fragen paar Fehler haben, das ist, warum die Daten anders aussehen.

Verwandte Themen