MongoDB聚合运算符:$getField

文章目录

$getField聚合运算符返回文档中指定字段的值,字段名可以包含点.或以$开头。如果不指定,$getField$$CURRENT作为字段返回。

语法

js 复制代码
{
  $getField: {
    field: <String>,
    input: <Object>
  }
}

字段说明:

  • field,字符串类型,指定数据对象中要返回的字段,可以是字符串表达式,如果字段以$符号开头,则需要把字段名放在$literal表达式返回。
  • input,对象类型,缺省值为$$CURRENT,可以是一个包含了指定字段值的表达式,input必须要能解析为一个对象、缺失、空或未定义,如果省略,默认为当前管道中处理的文档$$CURRENT

$$CURRENT返回字段值的简单写法如下:

js 复制代码
{
  $getField: <String>
}

使用

  • 如果field不是字符串类型,$getField返回错误
  • 如果input对象中不存在field或者未指定input$$CURRENT不不存在field字段,$getField返回missing
  • 如果input计算结果为missingundefinednull$getField返回null
  • 如果input计算结果不是对象、missingundefinednull,则$getField返回错误
  • $getField不会隐式遍历对象或数组,例如:$getField执行时会将fielda.b.c认为是a.b.c而不是嵌套字段{a:{b:{c}}}

举例

包含点号(.)的查询

inventory集合的内容如下:

json 复制代码
{ "_id" : 1, "item" : "sweatshirt", "price.usd": 45.99, qty: 300 }
{ "_id" : 2, "item" : "winter coat", "price.usd": 499.99, qty: 200 }
{ "_id" : 3, "item" : "sun dress", "price.usd": 199.99, qty: 250 }
{ "_id" : 4, "item" : "leather boots", "price.usd": 249.99, qty: 300 }
{ "_id" : 5, "item" : "bow tie", "price.usd": 9.99, qty: 180 }

下面的操作使用$getField$gt运算符查找价格price.usd超过200的产品:

js 复制代码
db.inventory.aggregate( [
  {
    $match:
      { $expr:
        { $gt: [ { $getField: "price.usd" }, 200 ] }
      }
   }
] )

操作返回下面的结果:

js 复制代码
[
  { _id: 2, item: 'winter coat', qty: 200, 'price.usd': 499.99 },
  { _id: 4, item: 'leather boots', qty: 300, 'price.usd': 249.99 }
]

查询以($)开头的字段

集合inventory有下面的文档:

json 复制代码
{ "_id" : 1, "item" : "sweatshirt", "$price": 45.99, qty: 300 }
{ "_id" : 2, "item" : "winter coat", "$price": 499.99, qty: 200 }
{ "_id" : 3, "item" : "sun dress", "$price": 199.99, qty: 250 }
{ "_id" : 4, "item" : "leather boots", "$price": 249.99, qty: 300 }
{ "_id" : 5, "item" : "bow tie", "$price": 9.99, qty: 180 }

下面的操作使用$getField$gt$literal运算符查找价格price大于200的产品:

js 复制代码
db.inventory.aggregate( [
  {
    $match:
      { $expr:
        { $gt: [ { $getField: {$literal: "$price" } }, 200 ] }
      }
   }
] )

操作返回下面的结果:

js 复制代码
[
  { _id: 2, item: 'winter coat', qty: 200, '$price': 499.99 },
  { _id: 4, item: 'leather boots', qty: 300, '$price': 249.99 }
]

子文档字段查询

使用下面的脚本创建inventory集合:

js 复制代码
db.inventory.insertMany( [
   { "_id" : 1, "item" : "sweatshirt",  "price.usd": 45.99,
     "quantity": { "$large": 50, "$medium": 50, "$small": 25 }
   },
   { "_id" : 2, "item" : "winter coat", "price.usd": 499.99,
     "quantity": { "$large": 35, "$medium": 35, "$small": 35 }
   },
   { "_id" : 3, "item" : "sun dress", "price.usd": 199.99,
     "quantity": { "$large": 45, "$medium": 40, "$small": 5 }
   },
   { "_id" : 4, "item" : "leather boots", "price.usd": 249.99,
     "quantity": { "$large": 20, "$medium": 30, "$small": 40 }
   },
   { "_id" : 5, "item" : "bow tie", "price.usd": 9.99,
     "quantity": { "$large": 0, "$medium": 10, "$small": 75 }
   }
] )

下面的操作返$small的值小于等于20的文档:

js 复制代码
db.inventory.aggregate( [
   { $match:
      { $expr:
         { $lte:
            [
               { $getField:
                  { field: { $literal: "$small" },
                    input: "$quantity"
                  }
               },
               20
            ]
         }
      }
   }
] )
  • $lte 运算符用于查找小于等于20的文档
  • $getField需要明确的fieldinput参数,因为$small字段是子文档的一部分
  • 因为字段名前面有$符号,$getField使用$literal来计算"$small"

输出结果如下:

js 复制代码
[
  {
    _id: 3,
    item: 'sun dress',
    'price.usd': 199.99,
    quantity: { '$large': 45, '$medium': 40, '$small': 5 }
  }
]
相关推荐
随风飘的云17 小时前
MySQL的慢查询优化解决思路
数据库
IvorySQL21 小时前
PostgreSQL 技术日报 (3月7日)|生态更新与内核性能讨论
数据库·postgresql·开源
赵渝强老师1 天前
【赵渝强老师】金仓数据库的数据文件
数据库·国产数据库·kingbase·金仓数据库
随逸1771 天前
《Milvus向量数据库从入门到实战,手把手搭建语义检索系统》
数据库
神秘的猪头1 天前
🚀 React 开发者进阶:RAG 核心——手把手带你玩转 Milvus 向量数据库
数据库·后端·llm
IvorySQL2 天前
PostgreSQL 技术日报 (3月6日)|为什么 Ctrl-C 在 psql 里让人不安?
数据库·postgresql·开源
NineData2 天前
数据库管理工具NineData,一年进化成为数万+开发者的首选数据库工具?
运维·数据结构·数据库
IvorySQL2 天前
PostgreSQL 技术日报 (3月5日)|规划器控制力升级,内核能力再进阶
数据库·postgresql·开源
数据组小组3 天前
免费数据库管理工具深度横评:NineData 社区版、Bytebase 社区版、Archery,2026 年开发者该选哪个?
数据库·测试·数据库管理工具·数据复制·迁移工具·ninedata社区版·naivicat平替