Mongodb 对象数组与对象的Mongo索引

Mongodb 对象数组与对象的Mongo索引,mongodb,mongodb-indexes,Mongodb,Mongodb Indexes,我正在实现一个联系人数据库,它处理许多字段。其中大多数是预定义的,可以认为是绑定的,但也有一些是不绑定的。我们将这些字段中的一个称为“组”。我们目前的实施方式是(每个文档/联系人都有“组”字段): 但是读了一些书之后,我觉得我应该这样做: 'groups' : [ { 'id' : 152, 'name' : 'hi' }, { 'id' : 111, 'name' : 'group2' } ... ] 然后应用索引db.contact.ensureIndex({'group

我正在实现一个联系人数据库,它处理许多字段。其中大多数是预定义的,可以认为是绑定的,但也有一些是不绑定的。我们将这些字段中的一个称为“组”。我们目前的实施方式是(每个文档/联系人都有“组”字段):

但是读了一些书之后,我觉得我应该这样做:

'groups' : [
   { 'id' : 152, 'name' : 'hi' },
   { 'id' : 111, 'name' : 'group2' }
   ...
]
然后应用索引db.contact.ensureIndex({'groups.id':1})

我的问题是关于功能。这两种结构之间的区别是什么?索引实际上是如何构建的(它只是在每个文档/联系人中建立索引,还是构建一个包含所有文档/联系人的所有组的全面索引?)


我认为这在结构上是最好的方法,但如果我不正确,请告诉我。

在第二种情况下,查询肯定会容易得多,其中“groups”是一个子文档数组,每个子文档都有一个“id”和一个“name”

Mongo不支持“通配符”查询,因此,如果您的文档是以第一种方式构造的,并且您希望查找值为“hi”的子文档,但不知道键是152,那么您将无法执行此操作。使用第二种文档结构,您可以轻松地查询{“groups.name”:“hi”}

有关查询嵌入式对象的更多信息,请参阅标题为“点表示法(深入对象)”的文档 “高级查询”文档中的“数组中的值”和“嵌入对象中的值”部分也很有用:

对于{'groups.id':1}上的索引,将为每个文档中每个“groups”数组中的每个“id”键创建一个索引项。对于“组”上的索引,每个文档只创建一个索引项

如果您有第二种类型的文档,并且有一个关于组的索引,那么您的查询必须匹配整个子文档才能使用该索引。例如,给定文档:

{ "_id" : 1, "groups" : [ { "id" : 152, "name" : "hi" }, { "id" : 111, "name" : "group2" } ] }
询问

db.<collectionName>.find({groups:{ "id" : 152, "name" : "hi" }}) 
db..find({groups:{“id”:152,“name”:“hi”})
将使用索引,但查询

db.<collectionName>.find({"groups":{$elemMatch:{name:"hi"}}})
db..find({“组”:{$elemMatch:{name:“hi”}})

db..find({“groups.name”:“hi”})
不会

您创建的索引应该取决于您最常执行的查询

您可以使用.explain()命令试验查询使用的索引(如果有)。第一行“游标”将告诉您正在使用哪个索引。“游标”:“BasicCursor”表示正在执行完全收集扫描

文档中有关于索引的更多信息:

上述“索引数组元素”部分链接到标题为“多键”的文档:


希望这将提高您对如何查询嵌入文档以及如何使用索引的理解。如果您有任何后续问题,请告知我们

这是一个很好的答案,但前两个环节都断了。我一直在搜索,但在网上找不到他们的新位置。有什么帮助吗?您好,通过阅读您的回复,我想知道索引是否会用于查询,如
db..find({“groups”:{$elemMatch:{“id”:152}}})
@portforwardpodcast第一个链接似乎是
db.<collectionName>.find({"groups":{$elemMatch:{name:"hi"}}})
db.<collectionName>.find({"groups.name":"hi"})