Mongodb 使用合并对象而不覆盖子文档
我正在尝试合并聚合管道中的两个字段 我想改变这一点:Mongodb 使用合并对象而不覆盖子文档,mongodb,Mongodb,我正在尝试合并聚合管道中的两个字段 我想改变这一点: { "a": 1, "b": { "first": { "property_a": "some_value", "property_b": "some_value", "property_c": "some_value" }, "second": { "property_a": "some_value",
{
"a": 1,
"b": {
"first": {
"property_a": "some_value",
"property_b": "some_value",
"property_c": "some_value"
},
"second": {
"property_a": "some_value",
"property_b": "some_value",
"property_c": "some_value"
},
"third": {
"property_a": "some_value",
"property_b": "some_value",
"property_c": "some_value"
},
"fiftieth": {
"property_a": "some_value",
"property_b": "some_value",
"property_c": "some_value"
}
},
"c": {
"first": {
"property_x": "some_value",
"property_y": "some_value"
},
"second": {
"property_x": "some_value",
"property_y": "some_value"
},
"fiftieth": {
"property_x": "some_value",
"property_y": "some_value"
}
}
}
在这种情况下,无需指定“b”下列出的每个键:
在mergeObjects
的文档中,它指出:
合并对象在合并文档时覆盖字段值。如果要合并的文档包含相同的字段名,则结果文档中的字段具有上次合并文档中的值
如何在不指定每个键的情况下合并字段b和c的子文档(在我的实际用例中有85个键)。此外,字段c可能没有在b下列出所有键。或者这是不可能的 您可以使用
$objectToArray
将对象转换为k、v对,组合并$unwind
它们,$group
按键名并合并文档,然后$group
按_-id将键收集回一起
db.collection.aggregate([
{$addFields: {
combined: {
$concatArrays: [
{$objectToArray: "$b"},
{$objectToArray: "$c"}
]
}
}},
{$unwind: "$combined"},
{$group: {
_id: {_id: "$_id", key: "$combined.k"},
doc: {$first: "$$ROOT"},
v: {$mergeObjects: "$combined.v"}
}},
{$group: {
_id: "$_id._id",
doc: {$first: "$doc"},
combined: {$push: {
k: "$_id.key",
v: "$v"
}}
}},
{$addFields: {"doc.b": {$arrayToObject: "$combined"}}},
{$project: {
combined: 0,
"doc.c": 0
}},
{$replaceRoot: {newRoot: "$doc"}}
])
是否确定
b
或c
中的任何字段都不会包含文档以外的内容?是的。字段b和c仅包含文档。此解决方案有效。我真的很感谢你的帮助!非常感谢你!
db.collection.aggregate([
{$addFields: {
combined: {
$concatArrays: [
{$objectToArray: "$b"},
{$objectToArray: "$c"}
]
}
}},
{$unwind: "$combined"},
{$group: {
_id: {_id: "$_id", key: "$combined.k"},
doc: {$first: "$$ROOT"},
v: {$mergeObjects: "$combined.v"}
}},
{$group: {
_id: "$_id._id",
doc: {$first: "$doc"},
combined: {$push: {
k: "$_id.key",
v: "$v"
}}
}},
{$addFields: {"doc.b": {$arrayToObject: "$combined"}}},
{$project: {
combined: 0,
"doc.c": 0
}},
{$replaceRoot: {newRoot: "$doc"}}
])