$let(聚合)
定义
$let绑定变量 用于指定表达式中,并返回表达式的结果。
的
$let表达式具有以下语法{ $let: { vars: { <var1>: <expression>, ... }, in: <expression> } } 字段规范vars在
in表达式中可访问的变量赋值块。要分配变量,请指定变量名称的字符串并分配一个有效的表达式作为值。变量赋值在
in表达式外部没有意义,甚至在vars块本身内部也没有。in要评估的表达式。要在聚合表达式中访问变量,请使用双美元符号(
$$)作为变量名称的前缀,并将其用引号括起来。有关表达式的更多信息,请参阅表达式运算符。有关聚合管道中变量使用的信息,请参阅聚合表达式中的变量。
行为
如果在vars块中修改外部定义变量的值,新值仅在in表达式中生效。在in表达式外部,变量保留其先前的值。
在vars赋值块中,赋值的顺序不重要,变量赋值仅在in表达式中才有意义。因此,在vars赋值块中访问变量的值是指定在vars块外部的变量的值,而不是在相同的vars块内部。
例如,考虑以下$let表达式
{ $let: { vars: { low: 1, high: "$$low" }, in: { $gt: [ "$$low", "$$high" ] } } }
在vars赋值块中,"$$low"指的是外部定义的变量low的值,而不是在相同的vars块中定义的变量。如果在此$let表达式块外部未定义low,则表达式无效。
示例
销售集合包含以下文档
{ _id: 1, price: 10, tax: 0.50, applyDiscount: true } { _id: 2, price: 10, tax: 0.25, applyDiscount: false }
以下聚合在$let中使用了$project管道阶段来计算并返回每个文档的finalTotal
db.sales.aggregate( [ { $project: { finalTotal: { $let: { vars: { total: { $add: [ '$price', '$tax' ] }, discounted: { $cond: { if: '$applyDiscount', then: 0.9, else: 1 } } }, in: { $multiply: [ "$$total", "$$discounted" ] } } } } } ] )
聚合返回以下结果
{ "_id" : 1, "finalTotal" : 9.450000000000001 } { "_id" : 2, "finalTotal" : 10.25 }