Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/mongodb/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Mongodb 如何从数组中删除重复项(复杂对象)_Mongodb_Aggregation Framework - Fatal编程技术网

Mongodb 如何从数组中删除重复项(复杂对象)

Mongodb 如何从数组中删除重复项(复杂对象),mongodb,aggregation-framework,Mongodb,Aggregation Framework,在每一份文件中 记录是一个包含许多重复对象的数组 在buy_items中还包含许多重复的项目 我如何清理重复的项目 原始文件: 预期产出: 对于Michaels解决方案,输出可能如下所示 { "_id": "0005d116qwwewdq82a1b84f148fa6027d429f3e", "records": [ "date": new Date("1996-02-08T08:00:00+0800"), "buy_items": [ "5210 "

在每一份文件中

记录
是一个包含许多重复对象的数组

buy_items
中还包含许多重复的项目

我如何清理重复的项目

原始文件:

预期产出:

对于Michaels解决方案,输出可能如下所示

{
  "_id": "0005d116qwwewdq82a1b84f148fa6027d429f3e",
  "records": [
    "date": new Date("1996-02-08T08:00:00+0800"),
      "buy_items": [
        "5210 "
        "1234 ",
        " "
      ]
    ]
}

可以使用

db.collection.aggregate(
[
{$unwind:“$records”},
{$unwind:“$records.buy_items”},
{$group:{“\u id”:{id:$\u id”,日期:$records.date},购买物品:{$addToSet:$records.buy_items},
{$group:{“{U id”:“${U id.id”,记录:{$push:{“日期”:“${U id.date”,“购买物品”:“$buy_物品”}}}}},{$sort:{“records.0.date”:1},
{$out:“集合”}
]
)
运算符允许您在指定集合中写入聚合结果,或替换现有集合


更好地使用操作

var bulk=bulk=db.collection.initializeOrderedBulkOp(),
计数=0;
db.collection.aggregate([
{“$unwind”:“$records”},
{“$project”:{
“日期”:“$records.date”,
“购买商品”:{“$setcrossion”:“$records.buy_items”}
}}, 
{“$REWIND”:“$buy_项目”},
{“$group”:{
“_id”:{“id”:“$_id”,“date”:“$date”},
“购买物品”:{“$addToSet”:“$buy_物品”}
}},
{“$group”:{
“\u id”:“$\u id.id”,
“记录”:{“$push”:{
“日期”:“$\u id.date”,
“购买物品”:“$购买物品”
}}
}}
]).forEach(函数(doc){
bulk.find({“\u id”:doc.\u id}).updateOne({
“$set”:{“记录”:doc.records}
}); 
计数++;
如果(计数%500==0){
bulk.execute();
bulk=db.collection.initializeOrderedBulkOp();
} 
})
如果(计数%500!=0)
bulk.execute();
结果:

{
“_id”:“0005d116qwwewdq82a1b84f148fa6027d429f3e”,
“记录”:[
{
“日期”:ISODate(“2012-12-08T00:00:00Z”),
“购买物品”:[
" ",
"1234 ",
"5210 "
]
},
{
“日期”:ISODate(“1996-02-08T00:00:00Z”),
“购买物品”:[
"5210 "
]
}
]
}

如果要更新当前收藏而不创建新收藏并删除以前的收藏。我试过了,但是你应该运行两个不同的更新命令

第一次更新
记录了
不同的
,如下所示:

db.collectionName.update({},{"$set":{"records":db.collectionName.distinct('records')}})
db.collectionName.update({},{"$set":{"records.0.buy_items":db.collectionName.distinct('records.buy_items')}})
对于
buy_items
的第二次更新,使用
distinct
如下所示:

db.collectionName.update({},{"$set":{"records":db.collectionName.distinct('records')}})
db.collectionName.update({},{"$set":{"records.0.buy_items":db.collectionName.distinct('records.buy_items')}})
如果要避免两次更新查询,请按照Michael的回答进行操作。

您可以尝试使用光标的方法迭代每个文档属性,检查唯一性并按如下方式过滤不同的值:

db.collection.find().forEach(function(doc){
    var records = [], seen = {};
    doc.records.forEach(function (item){
         var uniqueBuyItems = item["buy_items"].filter(function(i, pos) {
            return item["buy_items"].indexOf(i) == pos;
         });
         item["buy_items"] = uniqueBuyItems;
         if (JSON.stringify(item["buy_items"]) !== JSON.stringify(seen["buy_items"])) {
            records.push(item);
            seen["buy_items"] = item["buy_items"];
         }         
    }); 
    doc.records = records;
    db.collection.save(doc);
})

您可以使用聚合框架:1。解开记录2。放松购买物品3。使用addToSet 4重新组合buy_项目。使用addToSet重新组合记录,然后迭代结果集并更新文档是否要更新集合或使用聚合显示?@yogesh更新集合