Wat je eerst nodig hebt, is een voorwaardelijke $sum
gebaseerd op de $cond
operator in de groepering voor elke waarde. Dan kunt u afzonderlijk $subtract
:
db.gas.aggregate([
{ "$group": {
"_id": "$timestamp",
"gas-in": {
"$sum": {
"$cond": [
{ "$eq": [ "$sensor", "gas-in" ] },
"$value",
0
]
}
},
"gas-out": {
"$sum": {
"$cond": [
{ "$eq": [ "$sensor", "gas-out"] },
"$value",
0
]
}
},
}},
{ "$project": {
"gasdifference": { "$subtract": [ "$gas-in", "$gas-out" ] }
}}
])
Wat de resultaten geeft:
{ "_id" : ISODate("2015-09-17T21:20:35Z"), "gasdifference" : 5.5 }
{ "_id" : ISODate("2015-09-17T21:14:35Z"), "gasdifference" : 0.5 }
Het alternatief is om de "gas-out"-waarden negatief te maken voor een enkele trap:
db.gas.aggregate([
{ "$group": {
"_id": "$timestamp",
"gasdifference": {
"$sum": {
"$cond": [
{ "$eq": [ "$sensor", "gas-in" ] },
"$value",
{ "$subtract": [ 0, "$value" ] }
]
}
}
}}
])
En dat zal efficiënter zijn.
Als u meer dan twee mogelijke "sensor"-waarden heeft, "nest" u gewoon de $cond
uitspraken:
db.gas.aggregate([
{ "$group": {
"_id": "$timestamp",
"gasdifference": {
"$sum": {
"$cond": [
{ "$eq": [ "$sensor", "gas-in" ] },
"$value",
{ "$cond": [
{ "$eq": [ "$sensor", "gas-out" ] },
{ "$subtract": [ 0, "$value" ] },
0
]}
]
}
}
}}
])
Aangezien het "ternaire" operators zijn ( if-then-else ), valt elke verdere logica onder de "else" voorwaarde.