mongodb - 按 ObjectId 数组对文档进行分组
问题描述
db.test.insert([
{ name: 'one', refs: [ObjectId('111'), ObjectId('222'), ObjectId('333')] },
{ name: 'two', refs: [ObjectId('222'), ObjectId('333')] },
{ name: 'three', refs: [ObjectId('222'), ObjectId('333'), ObjectId('111')] },
])
理想情况下,如果文档具有所有相同的引用(以及相同数量的引用),我不想对它们进行分组,不管它们在数组字段中的顺序是什么。像这样
[
{
names: ['one', 'three'],
},
{
names: ['two'],
}
]
据我了解,我需要:
refs
对元素进行排序- 将
ObjectId
s 转换为字符串 - 将所有 id 字符串连接到单个字符串并保存到特定字段
- 按该字段分组
请注意,真实文档足够大(例如,包含一些繁重的“数据”字段,refs
本身平均可以包含 0-10 个项目,最多 50 个),过滤后的输入可以包含数千个文档。
就生产力(CPU + RAM)而言,这会是最有效的方式吗?
更新
很抱歉没有提到一个重要的细节:还有其他非数组字段应该参与分组。例如
{
name: 'can',
color: 'green',
refs: [ObjectId(1), ObjectId(2)],
material: 'plastic',
price: 50,
}
说我需要按color
+ refs
+对它们进行分组material
解决方案
您可以使用单个$group
with $setUnion
:
db.test.aggregate([
{ $group: { _id: { $setUnion: "$refs" }, names: { $push: "$name" } } },
{ $unset: "_id" }
])
如果您有更多要分组的字段,只需将它们添加到_id
:
{ $group: {
_id: {
refs: { $setUnion: "$refs" },
color: "$color",
material: "$material"
},
names: { $push: "$name" }
} },
推荐阅读
- android - wordpress 和 android studio 之间的联系
- prometheus - 将布尔度量/表达式转换为计数器
- elasticsearch - 使用管道到管道通信时关闭 Logstash
- python - 在 Django 上测试表单
- c# - 从列表中删除
List 中存在行的位置 - ubuntu - 安装freeradius 2.2.8时生成文件错误#2 eap libeap rlm_eap all modules all src all
- .net - 如何修复 .Net Azure Function App 中的“由于对象的当前状态导致操作无效”错误?
- oracle-adf - 在弹出窗口中显示之前从托管 bean 中读取文本并设置其样式
- node.js - 上传图片时看不到内容
- haskell - 阴谋集团解决依赖问题