2015-05-29 144 views
0

我们有一个MongoDB NoSQL数据库,它包含一些数据。目前该数据库包含10M行。默认的_id字段被用作主键。 我们集合了三个变量:MongoDb使用索引缓慢查询

  • _id
  • 时间戳(索引:1)
  • 变量1(索引:1,CompoundIndex与时间戳)
  • 变量2
  • Variable3

我们希望将时间戳和变量1结合起来查询。 我们有一个时间戳和变量1的索引。另外,即使对于范围查询这是不正确的,我们也有一个复合索引(Timestamp,Variable1)。

没有当我们有像下面这样的查询时,性能非常差(~1分钟的执行时间)。

实例查询:

db.getCollection('XXX').find({$and:[ 
{timestamp:{$lte:1424195749000}}, 
{timestamp:{$gte:1424195649000}}, 
{Variable1:1} 
]}) 

查询中使用仅约在变量1场运行(100毫秒)。

getIndexes():

{ 
    "0" : { 
     "v" : 1, 
     "key" : { 
      "_id" : 1 
     }, 
     "name" : "_id_", 
     "ns" : "XXXXXX_DB.XXXData" 
    }, 
    "1" : { 
     "v" : 1, 
     "key" : { 
      "timestamp" : 1.0000000000000000 
     }, 
     "name" : "timestamp_1", 
     "ns" : "XXXXXX_DB.XXXData" 
    }, 
    "2" : { 
     "v" : 1, 
     "key" : { 
      "timestamp" : -1.0000000000000000 
     }, 
     "name" : "timestamp_-1", 
     "ns" : "XXXXXX_DB.XXXData" 
    }, 
    "3" : { 
     "v" : 1, 
     "key" : { 
      "variable1" : 1.0000000000000000 
     }, 
     "name" : "variable1_1", 
     "ns" : "XXXXXX_DB.XXXData" 
    }, 
    "4" : { 
     "v" : 1, 
     "key" : { 
      "timestamp" : 1.0000000000000000, 
      "variable1" : 1.0000000000000000 
     }, 
     "name" : "timestamp_1_variable1_1", 
     "ns" : "XXXXXX_DB.XXXData" 
    } 
} 
+1

您使用的是哪个版本的MongoDB?如果3.0或更高版本,您是否可以包含[explain]的结果(http://docs.mongodb.org/manual/reference/method/cursor.explain/#cursor.explain)? – marijnz0r

+1

你可以在你的集合上发布'getIndexes()'的结果吗? – bagrat

+0

FWIW,使用MongoDB 3.0进行小规模测试时。2,获胜计划使用索引'timestamp_1'和拒绝索引'Variable1_1'和'timestamp_1_Variable1_1'。在'{Variable1:1,timestamp:1}'上添加复合索引时,后者成为赢家。 –

回答

3

你需要{ Variable1: 1, timestamp: 1 }索引来加速该查询(用大写V - 您在查询中使用 “V ariable1”,但你的指数似乎对 “v ariable1”)


鉴于您的查询:

db.getCollection('XXX').find({$and:[ 
    {timestamp:{$lte:1424195749000}}, 
    {timestamp:{$gte:1424195649000}}, 
    {Variable1:1} 
]}) 

这里,优化器会看到,你有Variable1平等。所以这个领域是“最有限度的”。所以优化器会选择一个索引作为前缀。 { Variable: 1}不应该太糟糕。但{ Variable: 1, timestamp: 1}会更好。

请注意,你有多余的指标:

  • {timestamp:-1}不会增加太多{timestamp:1}
  • {Variable1: 1}是无用的,如果你有{Variable1: 1, timestamp: 1}
    (因为前者是后者的前缀)
  • {timestamp: 1}没用,如果你有{timestamp: 1, Variable1: 1}
    (因为前者是后者的前缀)