这个问题是关于如何使用MongoDB中的索引在嵌套文档中查找内容,而不必索引每个单独的子级别。 我在MongoDB中有一个集合“test”,基本上是这样的:
{
"_id" : ObjectId("50fdd7d71d41c82875a5b6c1"),
"othercol" : "bladiebla",
"scenario" : {
"1" : { [1,2,3] },
"2" : { [4,5,6] }
}}
场景具有多个键,每个文档可以具有场景的任何子集(即,从无到子集到全部)。另外:场景不能是一个数组,因为我需要它作为Python中的字典。我在“场景”字段中创建了一个索引 我的问题是我想在集合上选择,过滤具有特定价值的文档。所以这在功能上运行良好:
db.test.find({"scenario.1": {$exists: true}})
但是,它不会使用任何索引我已添加的场景。只有当我在“scenario.1”上放置索引时才使用索引。但是我可以拥有数千个(或更多)场景(并且该集合本身有100.000个记录),所以我不愿意! 所以我尝试了替代方案:
db.test.find({"scenario": "1"})
这将在场景中使用索引,但不会返回结果。使场景成为一个数组仍然会产生相同的索引问题。
我的问题清楚了吗?任何人都可以指出我如何在这里取得最佳表现吗?
P.S。我已经看到了这个:How to Create a nested index in MongoDB?但是在我的情况下这个解决方案是不可能的(由于场景数量很多)
答案 0 :(得分:4)
在这种情况下设置index on a subobject之类的{{3}}是没用的,因为它只会在您对完整的scenario
对象而不是单个字段进行过滤时使用(将其视为二进制blob比较)。
您需要在每个可能的字段(scenario
,"scenario.1"
等)上添加索引,或者通过执行以下操作来重写您的架构以摆脱动态键:< / p>
"sceanario.2"
然后,您可以向{
"_id" : ObjectId("50fdd7d71d41c82875a5b6c1"),
"othercol" : "bladiebla",
"scenario" : [
{ id: "1", value: [1,2,3] },
{ id: "2", value: [4,5,6] }
}}
添加单个索引,以支持您需要执行的查询。
我知道你说你需要scenario.id
成为一个字典,而不是一个数组,但我不知道你有多少选择。
答案 1 :(得分:2)
Johnny HK的答案是一个很好的解释答案,应该在一般情况下使用。如果您必须拥有许多方案并且不需要复杂的查询,我将建议您解决问题的解决方法。不要在方案字段下保留值,只需在该字段下保存方案的ID,并将值保存为文档中的另一个字段,并使用方案ID作为此字段的键。
示例:
{
"_id" : ObjectId("50fdd7d71d41c82875a5b6c1"),
"othercol" : "bladiebla",
"scenario" : [ "1", "2"],
"scenario_1": [1,2,3],
"scenario_2": [4,5,6]
}}
使用此架构,您可以使用场景索引来查找特定场景。但是,如果需要查询特定的方案值,则需要在每个方案值字段(即scenario_1,scenario_2等)上都有索引。如果需要为每个字段设置索引,则不要更改原始模式和为每个嵌套字段使用稀疏索引,这可能有助于减小索引的大小。