sql >> Database teknologi >  >> NoSQL >> MongoDB

Gruppér efter datointervaller

Der er datosammenlægningsoperatører tilgængelige for MongoDBs aggregeringsramme. Så for eksempel en $dayOfYear operator bruges til at hente denne værdi fra datoen til brug i gruppering:

db.collection.aggregate([
    { "$group": {
        "_id": { "$dayOfYear": "$datetime" },
        "total": { "$sum": "$count" }
    }}
])

Eller du kan bruge en datomatematisk tilgang i stedet for. Ved at anvende epokedatoen konverterer du datoobjektet til et tal, hvor matematikken kan anvendes:

db.collection.aggregate([
    { "$group": {
        "_id": { 
            "$subtract": [
                { "$subtract": [ "$datetime", new Date("1970-01-01") ] },
                { "$mod": [
                    { "$subtract": [ "$datetime", new Date("1970-01-01") ] },
                    1000 * 60 * 60 * 24
                ]}
            ]
        },
        "total": { "$sum": "$count" }
    }}
])

Hvis det, du leder efter, er intervaller fra et aktuelt tidspunkt, så er det, du ønsker, dybest set datomatematisk tilgang og arbejde i nogle betingelser via $cond operatør:

db.collection.aggregate([
    { "$match": {
        "datetime": { 
            "$gte": new Date(new Date().valueOf() - ( 1000 * 60 * 60 * 24 * 365 ))
        }
    }},
    { "$group": {
        "_id": null,
        "24hours": { 
            "$sum": {
                "$cond": [
                    { "$gt": [
                        { "$subtract": [ "$datetime", new Date("1970-01-01") ] },
                        new Date().valueOf() - ( 1000 * 60 * 60 * 24 )
                    ]},
                    "$count",
                    0
                ]
            }
        },
        "30days": { 
            "$sum": {
                "$cond": [
                    { "$gt": [
                        { "$subtract": [ "$datetime", new Date("1970-01-01") ] },
                        new Date().valueOf() - ( 1000 * 60 * 60 * 24 * 30 )
                    ]},
                    "$count",
                    0
                ]
            }
        },
        "OneYear": { 
            "$sum": {
                "$cond": [
                    { "$gt": [
                        { "$subtract": [ "$datetime", new Date("1970-01-01") ] },
                        new Date().valueOf() - ( 1000 * 60 * 60 * 24 * 365 )
                    ]},
                    "$count",
                    0
                ]
            }
        }
    }}
])

Det er i bund og grund den samme tilgang som SQL-eksemplet, hvor forespørgslen betinget evaluerer, om datoværdien falder inden for det påkrævede interval og beslutter, om værdien skal føjes til summen.

Den ene tilføjelse her er den ekstra $match trin for at begrænse forespørgslen til kun at handle på de elementer, der muligvis ville være inden for det maksimale et-årsinterval, du beder om. Det gør det en smule bedre end den præsenterede SQL, da et indeks kunne bruges til at filtrere disse værdier ud, og du behøver ikke at "brute force" gennem ikke-matchende data i samlingen.

Det er altid en god idé at begrænse inputtet med $match ved brug af en aggregeringspipeline.



  1. Fjern flere dokumenter fra mongo i en enkelt forespørgsel

  2. Fejl:Ingen unix-socket-understøttelse på Windows, der forbinder mongodb

  3. Maskering af PII i MongoDB, Cassandra og Elasticsearch med DarkShield:...

  4. Om char b-præfiks i Python3.4.1-klienten opret forbindelse til redis