Mongodb 如何编写自连接查询

Mongodb 如何编写自连接查询,mongodb,aggregation-framework,Mongodb,Aggregation Framework,我有简单的收集交易,保存用户和餐厅的信息 { "user_id" : "U1", "restaurant_id" : "R_1" } { "user_id" : "U2", "restaurant_id" : "R_1" } { "user_id" : "U1", "restaurant_id" : "R_3" } { "user_id" : "U1", "restaurant_id" : "R_4" } { "user_id" : "U2", "restaurant_id" : "R_4" }

我有简单的收集
交易
,保存用户和餐厅的信息

{ "user_id" : "U1", "restaurant_id" : "R_1" }
{ "user_id" : "U2", "restaurant_id" : "R_1" }
{ "user_id" : "U1", "restaurant_id" : "R_3" }
{ "user_id" : "U1", "restaurant_id" : "R_4" }
{ "user_id" : "U2", "restaurant_id" : "R_4" }
在这里,我需要找到用户id为U1和U2的用户之间的相关餐厅(即我想找到U1和U2都访问过的餐厅)

我应该收到如下输出:-

{ "_id" : "R_4", "users" : [ "U2", "U1" ] }
{ "_id" : "R_1", "users" : [ "U2", "U1" ] }
这意味着,用户U1U2都访问了餐厅r1r4

我是mongoDb的新手,所以在谷歌搜索之后,我编写了一个不起作用的示例查询

db.transactions.aggregate([
    {$match: {"user_id": {
        "$in": [ U1, U2]
    }}},
    {
        $lookup: {
           from: "transactions",
           localField: "restaurant_id",
           foreignField: "restaurant_id",
           as: "related_taste"
         }
    }
])
你想要的是结果的“联合”,它是这样的:

db.transactions.aggregate([
    { "$match": { "user_id": { "$in": [ "U1", "U2" ] } }},
    { "$group": {
      "_id": "$restaurant_id",
      "users": { "$addToSet": "$user_id" }
    }},
    { "$match": { "users": { "$all": [ "U1", "U2" ] } } }
])
它给出了输出:

{ "_id" : "R_4", "users" : [ "U2", "U1" ] }
{ "_id" : "R_1", "users" : [ "U2", "U1" ] }
其工作原理是,阶段在
restaurant\u id
值上累积,并通过
user\u id
值保留该分组键的“设置”

然后,我们再次使用该条件查看提供的
用户id
值“两个”都存在于我们为其收集“set”的餐厅中

因此,只有“一个”列出的用户访问的任何地方都将被丢弃,我们得到的结果只是两个用户访问的结果


对您的数据进行了更正:

{ "user_id" : "U1", "restaurant_id" : "R_1" }
{ "user_id" : "U2", "restaurant_id" : "R_1" }
{ "user_id" : "U1", "restaurant_id" : "R_3" }
{ "user_id" : "U1", "restaurant_id" : "R_4" }
{ "user_id" : "U2", "restaurant_id" : "R_4" }

另外,您是否正在尝试“加入”同一个集合?这是一个RDBMS概念,在这里并不真正适用。一般来说,有更好的方法可以做到这一点。@NeilLunn那么你能告诉我什么是最好的方法吗?是的,我在Mysql中应用了与我相同的逻辑,因为我对Mysql有很好的理解,但我是Mongo的新手,所以我不知道在这种情况下处理这种情况的最佳做法是什么。因为这不是SQL,所以我们发出的语句有点不同。您“可以”在这里使用
$lookup
,但它确实不是必需的,而且是我们不需要的开销。还有另一种方法。谢谢你,这就是我一直在寻找的,还有+1的解释