我有两个MongoDB集合,它们共享一个公共的_id.使用mongo shell,我希望在一个集合中查找在另一个集合中没有匹配的_id的所有文档.

例子:

> db.Test.insert({ "_id" : ObjectId("4f08a75f306b428fb9d8bb2e"), "foo" : 1 })
> db.Test.insert({ "_id" : ObjectId("4f08a766306b428fb9d8bb2f"), "foo" : 2 })
> db.Test.insert({ "_id" : ObjectId("4f08a767306b428fb9d8bb30"), "foo" : 3 })
> db.Test.insert({ "_id" : ObjectId("4f08a769306b428fb9d8bb31"), "foo" : 4 })
> db.Test.find()
{ "_id" : ObjectId("4f08a75f306b428fb9d8bb2e"), "foo" : 1 }
{ "_id" : ObjectId("4f08a766306b428fb9d8bb2f"), "foo" : 2 }
{ "_id" : ObjectId("4f08a767306b428fb9d8bb30"), "foo" : 3 }
{ "_id" : ObjectId("4f08a769306b428fb9d8bb31"), "foo" : 4 }
> db.Test2.insert({ "_id" : ObjectId("4f08a75f306b428fb9d8bb2e"), "bar" : 1 });
> db.Test2.insert({ "_id" : ObjectId("4f08a766306b428fb9d8bb2f"), "bar" : 2 });
> db.Test2.find()
{ "_id" : ObjectId("4f08a75f306b428fb9d8bb2e"), "bar" : 1 }
{ "_id" : ObjectId("4f08a766306b428fb9d8bb2f"), "bar" : 2 }

现在我想要一些查询,返回测试中的两个文档,其中_id与测试2中的任何文档都不匹配:

{ "_id" : ObjectId("4f08a767306b428fb9d8bb30"), "foo" : 3 }
{ "_id" : ObjectId("4f08a769306b428fb9d8bb31"), "foo" : 4 }

我try 过$not、$ne、$in的各种组合,但就是找不到正确的组合和语法.此外,我不介意是否先执行db.Test2.find({}, {"_id": 1}),保存到某个变量中,然后在第二个查询中使用该变量(尽管我也无法让它工作).

Update:Zachary指向$nin的答案回答了问题的关键部分.例如,这是有效的:

> db.Test.find({"_id": {"$nin": [ObjectId("4f08a75f306b428fb9d8bb2e"), ObjectId("4f08a766306b428fb9d8bb2f")]}})
{ "_id" : ObjectId("4f08a767306b428fb9d8bb30"), "foo" : 3 }
{ "_id" : ObjectId("4f08a769306b428fb9d8bb31"), "foo" : 4 }

但是(承认这是不可伸缩的,但无论如何都要try ,因为在这种情况下这不是问题)我仍然无法在shell中组合这两个查询.这是我能得到的最接近的结果,这显然不太理想:

vals = db.Test2.find({}, {"_id": 1}).toArray()
db.Test.find({"_id": {"$nin": [ObjectId(vals[0]._id), ObjectId(vals[1]._id)]}})

是否有方法仅返回find命令中的值,以便将VAL直接用作$nin的数组输入?

推荐答案

在mongo 3.2中,以下代码似乎可以工作

db.collectionb.aggregate([
  {
    $lookup: {
        from: "collectiona",
        localField: "collectionb_fk",
        foreignField: "collectiona_fk",
        as: "matched_docs"
      }
   },
   {
      $match: {
        "matched_docs": { $eq: [] }
      }
   }
]);

基于这https://docs.mongodb.com/manual/reference/operator/aggregation/lookup/#use-lookup-with-an-array个例子

Mongodb相关问答推荐

如何使用ID数组对一个集合中的金额求和并更新另一个集合中的字段?

如何在MongoSH中的现有文档中插入字段

MongoDB聚合如何对对象数组中的值求和

在不知道字段名称的情况下如何引用 MongoDB 中的字段?

如何在MongoDB中搜索有序子集的方法?

仅当特定字段存在于 MongoDB 中时才更新它

Mongodb Timeseries / Golang - ['timestamp' 必须存在并包含有效的 BSON UTC 日期时间值]

尽管前一阶段输出文档,$group stage 仍返回零文档

mongo shell 命令不接受使用 db 命令

Nestjs中不同语言数据的mongodb聚合代码

如何将查询结果(单个文档)存储到变量中?

将 MongoDB 地理空间索引与 3d 数据结合使用

Meteor mongo 驱动程序可以处理 $each 和 $position 运算符吗?

MongoDB 2.1 聚合框架总和匹配名称的数组元素

带有 mongodb 和 nodejs 的实时 Web 应用程序

我怎样才能更快地scrape

mongodb 模式设计命名约定

Mongodb 约定包

MongoDB count() 未定义

将新值推送到 mongodb 内部数组 - mongodb/php