我的mongodb数据库包含每个设备每分钟的文档。我有一个查询基本上搜索与月份字段匹配的文档。
db.data.aggregate([
{
"$match":{ dId:14,month:6}
},
{
"$project" :{
dayOfMonth_agg :{$dayOfMonth : "$ts"},
month : "$month",
year_agg : {$year : "$ts"},
hour_agg : {$hour : "$ts"},
a0 :1,
a1:1,
d2:1,
f0:1,
dId:1
}
},
{
"$match":{year_agg:2017}
},
{
$group :{
_id : "$dayOfMonth_agg",
totalEnergy : { $sum: { $multiply: [{$subtract:["$a1","$a0"]},"$f0"] } },
avg_d0:{$avg:"$a0"},
avg_d1:{$avg:"$a1"},
avg_d2:{$avg:"$d2"},
}
},
{
$sort:{"_id":1}
}
])
我想优化查询性能,因此我将复合索引添加为:
db.data.createIndex({dId:1,month:1})
现在,在执行统计信息中,当创建dId上的单个索引时,docsExamined等于stats的值。 在dId上使用单个索引的Exec统计数据:
"keysExamined" : 103251,
"docsExamined" : 103251,
"hasSortStage" : true,
"cursorExhausted" : true,
"numYield" : 814,
"locks" : {
"Global" : {
"acquireCount" : {
"r" : NumberLong(1654)
}
},
"Database" : {
"acquireCount" : {
"r" : NumberLong(827)
}
},
"Collection" : {
"acquireCount" : {
"r" : NumberLong(826)
}
}
},
"nreturned" : 8,
"responseLength" : 770,
"protocol" : "op_command",
"millis" : 656,
"planSummary" : "IXSCAN { dId: 1 }",
"ts" : ISODate("2017-11-15T08:41:50.782Z"),
具有复合指数(dId和月)的执行数据
"keysExamined" : 103251,
"docsExamined" : 103251,
"hasSortStage" : true,
"cursorExhausted" : true,
"numYield" : 810,
"locks" : {
"Global" : {
"acquireCount" : {
"r" : NumberLong(1646)
}
},
"Database" : {
"acquireCount" : {
"r" : NumberLong(823)
}
},
"Collection" : {
"acquireCount" : {
"r" : NumberLong(822)
}
}
},
"nreturned" : 8,
"responseLength" : 770,
"protocol" : "op_command",
"millis" : 678,
"planSummary" : "IXSCAN { dId: 1, month: 1 }",
"ts" : ISODate("2017-11-15T08:45:38.536Z"),
"client" : "127.0.0.1",
"appName" : "MongoDB Shell",
"allUsers" : [ ],
"user" : ""
据我所知,与单一索引相比,docsExamined应该减少了。 为什么会这样?
编辑:请参阅第一条评论以获取答案