我有一个听起来相当简单的任务,我想使用 MongoDB 的聚合管道来实现。我想将一个字段中的数组视为集合(即,忽略顺序和重复),并按它们进行分组。例如,该集合可能是:
[
{
_id: 1
names: ["a", "b"]
},
{
_id: 2
names: ["c", "a"]
},
{
_id: 3
names: ["b", "a"]
}
]
我想要返回的结果是这样的:
[
{
names: ["a", "b"],
count: 2
},
{
names: ["a", "c"],
count: 1
}
]
谢谢!
最佳答案
您需要$sort
结果使它们对于分组键一致。确实没有其他办法:
db.collection.aggregate([
{ "$unwind": "$names" },
{ "$sort": { "_id": 1, "names": 1} },
{ "$group": {
"_id": "$_id",
"names": { "$push": "$names" }
}},
{ "$group": {
"_id": "$names",
"count": { "$sum": 1 }
}}
])
按照您的要求返回:
[
{
"_id": ["a", "b"],
"count": 2
},
{
"_id": ["a", "c"],
"count": 1
}
]
虽然有很多像“集合”这样的数组操作符,但它们都没有将数组内容“重新排序”为分组时适用的一致方式。仅当您 $sort
时才会完成此操作。
即使数组包含“重复项”,并且应用了一些集合转换,它们的顺序仍然不一致:
db.testa.insert_many([
{ "a" : [ "a", "b" ] },
{ "a" : [ "b", "a" ] },
{ "a" : [ "b", "a", "a" ] }
])
db.testa.aggregate({ "$project": { "_id": 0, "a": { "$setUnion": [ "$a", [] ] } } })
该示例当然会返回:
{ "a" : [ "b", "a" ] }
{ "a" : [ "a", "b" ] }
{ "a" : [ "a", "b" ] }
因此,您“仍然”需要 $unwind
和 $sort
以获得用于分组目的的一致“集”。
关于mongodb - 按数组对文档进行分组,将数组视为一个集合,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36213762/