【问题标题】:mongodb $lookup + regexmongodb $查找+正则表达式
【发布时间】:2017-01-11 22:46:50
【问题描述】:

Mongo 用户,我有一个问题,非常感谢您的帮助。

我有三个 mongo 集合,它们的行为类似于关系数据库表:

contacts_collecion

{
    "_id" : ObjectId("..."),
    "cid" : "1",
    "email" : "a1@a.aaa"
}
{
    "_id" : ObjectId("..."),
    "cid" : "2",
    "email" : "a2@a.aaa"
}
{
    "_id" : ObjectId("..."),
    "cid" : "3",
    "email" : "a3@a.aaa"
}

groups_collection

{
    "_id" : ObjectId("..."),
    "gid" : "1",
    "group_name" : "group1"
}
{
    "_id" : ObjectId("..."),
    "gid" : "1",
    "group_name" : "group2"
}

contacts_groups_collection

{
    "_id" : ObjectId("..."),
    "cid" : "2",
    "gid" : "1"
}
{
    "_id" : ObjectId("..."),
    "cid" : "3",
    "gid" : "1"
}
{
    "_id" : ObjectId("..."),
    "cid" : "3",
    "gid" : "2"
}

所以我有一对多的关系 - 每个联系人都可以在每个组中。 我想用 mongo equivalnet of sql 查询 mongodb

SELECT contacts.*
FROM  dbo.contacts INNER JOIN dbo.contacts_groups ON dbo.contacts.cid = dbo.contacts_groups.cid
WHERE dbo.contacts.email LIKE '%a%' AND dbo.contacts_groups.gid = '1'
ORDER BY dbo.contacts.email

1) 我知道如何构建第一个过滤器 (WHERE dbo.contacts.email LIKE '%a%')。

db.contacts.find({"email": /a/})

使用“C#/.NET 驱动程序版本 2.3”我可以做到(我还需要分页,所以我有:

FilterDefinition<ContactSerial> filter = Builders<ContactSerial>.Filter.Regex("Email", "aaa");
List<ContactSerial> contactsList = m_mongoConn.ContactsColl.Find(filter).Skip(0).Limit(5).ToList();

2) 我想如何实现 INNER JOIN 的等效(不理想)(即使 mongo 不是关系数据库)。
我找到了$lookupdb.contacts.aggregate([{ $lookup: {from: "contacts_groups", localField: "cid", foreignField: "cid", "as": "details"}}])

使用“C#/.NET 驱动程序 2.3 版”:mongoConn.ContactsColl.Aggregate().Lookup("contacts_groups", "cid", "cid", "details");
$lookup 会给我

{
    "_id" : ObjectId("..."),
    "cid" : "1",
    "email" : "a1@a.aaa",
    "details" : [ ]
}
{
    "_id" : ObjectId("..."),
    "cid" : "2",
    "email" : "a2@a.aaa",
    "details" : [
            {
                    "_id" : ObjectId("..."),
                    "cid" : "2",
                    "gid" : "1"
            }
    ]
}
{
    "_id" : ObjectId("..."),
    "cid" : "3",
    "email" : "a3@a.aaa",
    "details" : [
            {
                    "_id" : ObjectId("..."),
                    "cid" : "3",
                    "gid" : "1"
            },
            {
                    "_id" : ObjectId("..."),
                    "cid" : "3",
                    "gid" : "2"
            }
    ]
}


我的问题是:
a) 如何在一个 MongoShell 查询中结合正则表达式过滤器 (1) 和 $lookup (2)?
如何使用 “C#/.NET 驱动程序版本 2.3” 做到这一点
b) 如何在 MongoShell 查询中添加第二个过滤器 (AND dbo.contacts_groups.group_id = '1') - 请注意,这是来自第二个集合:联系人组不是联系人
“C#/.NET Driver Version 2.3”如何?
c) 如何添加到所有这些 (ORDER BY dbo.contacts.email)

【问题讨论】:

    标签: c# mongodb mongodb-query mongodb-.net-driver


    【解决方案1】:

    1) 要为聚合查询预过滤值,请使用 match

    db.contacts.aggregate([
      {$match:{email: {"$regex":/a/}}},
      {$lookup: {from: "contacts_groups", localField: "cid", foreignField: "cid", "as": "details"}}])
    

    您还可以在 c# 中使用预定义的过滤器进行聚合:

    m_mongoConn.ContactsColl
             .Aggregate()
             .Match(filter)
             .Lookup("contacts_groups", "cid", "cid", "details")
    

    2) 查找后需要执行另一个项目。在此处查看示例:Filter $lookup results

    3) 要对聚合管道中的输出进行排序,可以使用Sort。请注意,在您的聚合中,您从 Match 获得 Contacts,但在 Lookup 之后,您只有 Bson。因此,最好在MatchLookup之间进行排序

    m_mongoConn.ContactsColl
             .Aggregate()
             .Match(filter)
             .Sort(Builders<ContactSerial>.Sort.Ascending(c=>c.email))
             .Lookup("contacts_groups", "cid", "cid", "details")
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-08-03
      相关资源
      最近更新 更多