MongoDB如何筛选子数组中label字段数量小于数组总长度的文档
两种方式都可以实现,优先使用带$expr的find()即可,写法更简洁,性能也和aggregate()无差异。
find()实现方案(MongoDB 3.6及以上版本支持)
db.your_collection.find({ // 先过滤出analysis存在、不为空且是数组的文档,避免后续计算报错 analysis: { $exists: true, $ne: null, $isArray: true }, $expr: { // 带label的元素长度 < 数组总长度 $lt: [ // 计算数组中存在label字段的元素数量 { $size: { $filter: { input: "$analysis", cond: { $ne: ["$$this.label", undefined] } } }}, // 数组总长度 { $size: "$analysis" } ] } })
如果你使用的MongoDB版本低于4.4,把
$isArray: true替换为$type: "array"即可兼容。
aggregate()实现方案
如果筛选后还需要对文档做分组、关联等其他聚合操作,可以用aggregate(),筛选逻辑和上面完全一致,放在$match阶段即可:
db.your_collection.aggregate([ { $match: { analysis: { $exists: true, $ne: null, $isArray: true }, $expr: { $lt: [ { $size: { $filter: { input: "$analysis", cond: { $ne: ["$$this.label", undefined] } } } }, { $size: "$analysis" } ] } } } // 可继续追加其他聚合阶段 ])
原有查询错误原因
你之前写的"analysis.label": { $exists: false }语义是「数组中不存在任何带label字段的元素」,也就是只能匹配所有analysis元素都没有label的文档,不符合「部分有label、部分没有」的筛选需求。
内容的提问来源于stack exchange,提问作者01hanst
相关产品推荐
相关产品推荐

