mongodb - MongoDB 聚合错误 $in 需要一个数组
问题描述
下面是我的文档,我想过滤所有这些邮政编码以及它们对应res_count
的也存在于名为data
.
文档 :
{ "data" : [ "10451", "10458", "10467", "10461", "10462" ] }
{ "zipcode" : "10470", "res_count" : 8 }
{ "zipcode" : "10454", "res_count" : 10 }
{ "zipcode" : "10466", "res_count" : 11 }
{ "zipcode" : "10455", "res_count" : 9 }
{ "zipcode" : "10462", "res_count" : 29 }
{ "zipcode" : "10461", "res_count" : 25 }
{ "zipcode" : "10467", "res_count" : 15 }
{ "zipcode" : "10465", "res_count" : 28 }
{ "zipcode" : "10452", "res_count" : 11 }
{ "zipcode" : "10469", "res_count" : 10 }
{ "zipcode" : "10459", "res_count" : 7 }
{ "zipcode" : "10457", "res_count" : 14 }
{ "zipcode" : "10451", "res_count" : 68 }
{ "zipcode" : "10463", "res_count" : 28 }
{ "zipcode" : "10458", "res_count" : 34 }
{ "zipcode" : "10468", "res_count" : 12 }
{ "zipcode" : "10475", "res_count" : 14 }
{ "zipcode" : "10474", "res_count" : 10 }
{ "zipcode" : "10473", "res_count" : 3 }
我尝试使用$in
,但它说"errmsg" : "$in needs an array"
解决方案
由于您data
只在一个文档中输入了字段。所以如果你运行类似$in
的$match
东西{$match : {$in : ['$zipcode', '$data']}}
会抛出同样的错误"errmsg" : "$in needs an array"
。
但为什么 ?
通常,聚合管道阶段对集合文档执行操作,以原子方式处理每个文档,因此您不能将一个文档的字段用于其他文档。(例如:-如果您尝试$addFields
添加一个新字段 'dataCopy' 取自$data
- addFields 不会向不存在 'data' 字段的文档添加任何新字段)。$group
因此,为了执行此操作,您需要使用以下聚合查询将集合中的所有文档带到一个文档中:
db.collection.aggregate([
/** Iterate on all docs & push document which has 'data' field into 'dataDoc' &
* push all other docs into 'allDocs' array field
*/
{
$group: {
_id: "",
dataDoc: {
$push: {
$cond: [{ $eq: [{ $type: "$data" }, "array"] }, "$$ROOT", "$$REMOVE"]
}
},
allDocs: {
$push: {
$cond: [
{ $eq: [{ $type: "$zipcode" }, "string"] },
"$$ROOT",
"$$REMOVE"
]
}
}
}
},
/** Unwind dataDoc array to make it 'dataDoc' field of type object */
{
$unwind: "$dataDoc"
},
/** Re-create 'allDocs' array field with objects which meet required condition,
* newly formed array will have docs whose zipcode exists in data array
* */
{
$addFields: {
allDocs: {
$filter: {
input: "$allDocs",
cond: { $in: ["$$this.zipcode", "$dataDoc.data"] }
}
}
}
},
/** Unwind 'allDocs' array */
{
$unwind: "$allDocs"
},
/** Make 'allDocs' object field as new root, after this your result will have docs
* whose zipcode exists in data array
*/
{
$replaceRoot: {
newRoot: "$allDocs"
}
}
]);
测试: MongoDB-游乐场
推荐阅读
- python-3.x - Python 解析 XML 文件并更新内容
- c# - 如何获取远程计算机上次输入(空闲)时间
- android - AlarmManager 向应用程序返回数据
- .net - 在调试降级您的 .net 版本时可以附加到进程吗?
- sql - 以json格式将一列数据复制到另一列
- javascript - 如何使用异步系统在 django 模板中加载图像?
- c - 十六进制字符位旋转
- java - 使用 Aspose 库将 PDF 转换为 HTML 后,将 html 内容适合页面问题
- java - 如何在 Quarkus Main 方法中注册一个 bean
- prometheus - metric_relabel_configs 中的 Prometheus 类型转换