我有一个如下的Mongo文档。在这里,项目就像第一个项目在数组索引0上,第二个项目在数组索引1上,第三个项目在数组索引2上.....
{
"_id": "234463456453643563456",
"name": "Mike",
"empId": "10",
"managerId": "8",
"projects" : [ "123", "456", "789"]
}
我在项目字段中有索引,我想搜索第一个项目为123,第二个项目为456 ...的员工...
我的索引如下,
createIndex({"projects":1});
当我进行如下搜索时,需要花费时间。
{“ $ or”:[{“ projects.2”:“ 123”},{“ projects.4”:“ 456”},{ “ projects.3”:“ 789”},{“ projects.1”:“ 5467”},{“ projects.0”: “ 9768”}]}
但是,相同的查询在创建索引后效果非常好。
createIndex({"projects.0":1});
createIndex({"projects.1":1});
createIndex({"projects.2":1});
createIndex({"projects.3":1});
createIndex({"projects.4":1});
createIndex({"projects.5":1});
创建索引后,每个查询可节省3秒钟。
内部如何运作?为什么会有如此大的差异?
答案 0 :(得分:1)
如果使用explain命令,很容易看到它是如何工作的。快速摘要:
我的测试集:
{
"_id" : ObjectId("5b7fa665844b5ebfad064b1c"),
"arr" : [ "123", "456", "789"]
},
{
"_id" : ObjectId("5b80f96e9fceda195ba853af"),
"arr" : [ "ABC", "DEF", "FOO"]
}
我的索引:createIndex({"arr":1})
现在,如果我以find({arr: '123'}).explain()
的身份进行搜索,我们将从explain result
中看到:
...
"indexName" : "_arr_",
"isMultiKey" : true,
"multiKeyPaths" : {
"arr" : [
"arr"
]
},
...
使用了正确的索引。现在find({arr.0: '123'}).explain()
呢?
...
"winningPlan" : {
"stage" : "COLLSCAN",
"filter" : {
"arr.0" : {
"$eq" : "123"
}
},
"direction" : "forward"
},
...
现在,我们获得了一个不错的完整COLLSCAN
作为“获奖”计划:)。
接下来createIndex({"arr.0":1});
,然后find({arr.0: '123'}).explain()
给我们:
...
"winningPlan" : {
"stage" : "FETCH",
"inputStage" : {
"stage" : "IXSCAN",
"keyPattern" : {
"arr.0" : 1
},
"indexName" : "_arr.0_",
"isMultiKey" : false,
"multiKeyPaths" : {
"arr.0" : []
},
"isUnique" : false,
"isSparse" : false,
"isPartial" : false,
"indexVersion" : 2,
"direction" : "forward",
"indexBounds" : {
"arr.0" : [
"[\"123\", \"123\"]"
]
}
}
}
...
因此,如您所见,如果要按数组索引搜索,arr
上的multiKey索引是不够的,因为:
MongoDB为数组中的每个元素创建一个索引键。这些 多键索引支持对数组字段的高效查询
因此,这正是您执行初始索引时发生的事情……mongo找到包含123
的文档,但是在您的情况下,您想进入需要单个索引的特定数组索引查询索引,如explain
所示。
希望这对您有所帮助。