我正在使用MongoDB聚合框架展开数组,并且该数组有重复数据,我需要在进行进一步分组时忽略这些重复数据。
我怎样才能做到这一点?
答案 0 :(得分:43)
您可以使用$addToSet执行此操作:
db.users.aggregate([
{ $unwind: '$data' },
{ $group: { _id: '$_id', data: { $addToSet: '$data' } } }
]);
如果没有看到您的实际查询,很难给出更具体的答案。
答案 1 :(得分:24)
你必须使用$ addToSet,但首先你必须按_id分组,因为如果你不这样做,你将在列表中的每个项目中获得一个元素。
想象一下,收藏的帖子包含以下文档:
{
body: "Lorem Ipsum...",
tags: ["stuff", "lorem", "lorem"],
author: "Enrique Coslado"
}
想象一下,您想要计算每位作者最常用的标签。你可以像这样进行聚合查询:
db.posts.aggregate([
{$project: {
author: "$author",
tags: "$tags",
post_id: "$_id"
}},
{$unwind: "$tags"},
{$group: {
_id: "$post_id",
author: {$first: "$author"},
tags: {$addToSet: "$tags"}
}},
{$unwind: "$tags"},
{$group: {
_id: {
author: "$author",
tags: "$tags"
},
count: {$sum: 1}
}}
])
这样你就会得到这样的文件:
{
_id: {
author: "Enrique Coslado",
tags: "lorem"
},
count: 1
}
答案 2 :(得分:0)
先前的回答是正确的,但是可以简化执行$unwind -> $group -> $unwind
的过程。
您可以使用$addFields
+ $reduce
将已包含唯一条目的已过滤数组传递到管道,然后仅$unwind
传递一次。
示例文档:
{
body: "Lorem Ipsum...",
tags: [{title: 'test1'}, {title: 'test2'}, {title: 'test1'}, ],
author: "First Last name"
}
查询:
db.posts.aggregate([
{$addFields: {
"uniqueTag": {
$reduce: {
input: "$tags",
initialValue: [],
in: {$setUnion: ["$$value", ["$$this.title"]]}
}
}
}},
{$unwind: "$uniqueTag"},
{$group: {
_id: {
author: "$author",
tags: "$uniqueTag"
},
count: {$sum: 1}
}}
])