Den generelle forespørgsel her er at inkludere intervallet for "month"
værdier i betragtning, hvor den er "større end" -5
måneder "før" og "mindre end" +2
måneder "efter" som registreret i den "enrolled"
matrixindgange.
Problemet er, at da disse værdier er baseret på "dateJoined"
, skal de justeres med det korrekte interval mellem "dateJoined"
og "dateActivated"
. Dette gør udtrykket effektivt:
monthsDiff = (yearActivated - yearJoined)*12 + (monthActivated - monthJoined)
where month >= ( startRange + monthsDiff ) and month <= ( endRange + monthsDiff )
and enrolled = "01"
Eller logisk udtrykt "Månederne mellem det udtrykte interval justeret med antallet af måneders forskel mellem tilmelding og aktivering" .
Som angivet i kommentaren, er det allerførste, du skal her, at gemme disse datoværdier som en BSON Date
i modsætning til deres nuværende tilsyneladende "streng"-værdier. Når det er gjort, kan du derefter anvende følgende aggregering for at beregne forskellen fra de angivne datoer og filtrere det justerede interval i overensstemmelse hermed fra arrayet, før du tæller:
var rangeStart = -5,
rangeEnd = 2;
db.getCollection('enrollments').aggregate([
{ "$project": {
"enrollments": {
"$size": {
"$filter": {
"input": "$enrolled",
"as": "e",
"cond": {
"$let": {
"vars": {
"monthsDiff": {
"$add": [
{ "$multiply": [
{ "$subtract": [
{ "$year": "$dateActivated" },
{ "$year": "$dateJoined" }
]},
12
}},
{ "$subtract": [
{ "$month": "$dateActivated" },
{ "$month": "$dateJoined" }
]}
]
}
},
"in": {
"$and": [
{ "$gte": [ { "$add": [ rangeStart, "$$monthsDiff" ] }, "$$e.month" ] },
{ "$lte": [ { "$add": [ rangeEnd, "$$monthsDiff" ] }, "$$e.month" ] },
{ "$eq": [ "$$e.enrolled", "01" ] }
]
}
}
}
}
}
}
}}
])
Så dette gælder det samme $filter
til det array, som du forsøgte, men tager nu også højde for de justerede værdier for de måneder, der skal filtreres efter.
For at gøre dette lettere at læse anvender vi $let
som tillader beregning af den fælles værdi opnået for $$monthsDiff
som implementeret i en variabel. Det er her, det oprindeligt forklarede udtryk anvendes ved at bruge $year
og $month
for at udtrække disse numeriske værdier fra de lagrede datoer.
Brug af de ekstra matematiske operatorer $add
, $subtract
og $multiply
du kan både beregne forskellen i måneder og også senere anvende til at justere "range"-værdierne i de logiske forhold med $gte
og $lte
.
Endelig fordi $filter
udsender en række kun de poster, der matcher betingelserne, for at "tælle" anvender vi $size
som returnerer længden af det "filtrerede" array, som er "antal" af matches.
Afhængigt af dit tilsigtede formål kan hele udtrykket også leveres i argument til $sum
som en $group
akkumulator, hvis det da virkelig var hensigten.