【问题标题】:Does mongodb aggregation use sparse indexesmongodb聚合是否使用稀疏索引
【发布时间】:2017-02-13 23:19:08
【问题描述】:

使用 mongo 3.2。

试图查找信息,mongodb聚合是否使用稀疏索引。

  1. https://docs.mongodb.com/manual/core/aggregation-pipeline-optimization/

    当放置在管道的开头时,$match 操作使用合适的索引来仅扫描集合中的匹配文档。

  2. https://docs.mongodb.com/manual/core/index-sparse/

    即使按索引字段排序,MongoDB 也不会选择稀疏索引来完成查询以返回完整的结果:...要使用稀疏索引,请使用hint() 显式指定索引

所以,问题是,如果我有稀疏索引,mongo 聚合管道是否会匹配索引字段?

【问题讨论】:

  • 嗨,聚合框架可以选择添加 explain 选项 - 如果您已经有示例数据和索引,只需添加 explain 选项,如下所示:db.orders.aggregate( [ { $match: { status: "A" } }, { $group: { _id: "$cust_id", total: { $sum: "$amount" } } }, { $sort: { total: -1 } } ], { explain: true } ) 它会让您知道它是否使用它。
  • @cohenjo explain in aggregation 不提供 executionStats,这就是为什么无法使用稀疏索引检查是否是聚合。

标签: mongodb indexing aggregation-framework


【解决方案1】:

是的,MongoDB 聚合将使用合适的稀疏索引,除非稀疏索引会为某个查询返回不完整的结果。

问题中的摘录 2 解释了一个稀疏索引会为某个查询返回不完整结果的示例。如果查询对稀疏字段排序,但不对其进行过滤,则无法使用该索引,因为结果将不完整(缺少该字段的文档会被错误地排除)。

另一种无法使用稀疏索引的情况是,您在字段上进行过滤,但使用{ x: { $exists: false } } 之类的查询,其中稀疏索引将不包含匹配结果(因为它专门排除了它们)。

在您所说的情况下,$match 正在使用稀疏索引过滤字段,可以使用稀疏索引如果索引将包含完整结果,例如您正在检查相等性或使用比较运算符,如$gte 等,但不是$ne{ $exists: false } 等运算符。

即使没有executionStats,您也可以使用说明命令进行确认。

从带有{$match:{a:4}} 和未索引字段a 的测试聚合查询,执行集合扫描:

"winningPlan" : {
    "stage" : "COLLSCAN",
    "filter" : {
        "a" : {
            "$eq" : 4
        }
    },
    "direction" : "forward"
},

从带有稀疏索引字段b{$match:{b:4}} 的测试聚合查询中,使用了稀疏索引:

"winningPlan" : {
  "stage" : "FETCH",
  "inputStage" : {
      "stage" : "IXSCAN",
      "keyPattern" : {
          "b" : 1
      },
      "indexName" : "b_1",
      "isMultiKey" : false,
      "isUnique" : false,
      "isSparse" : true,
      "isPartial" : false,
      "indexVersion" : 1,
      "direction" : "forward",
      "indexBounds" : {
          "b" : [
              "[4.0, 4.0]"
          ]
      }
  }
},

对于在稀疏索引字段b 上使用{$match:{b:{$exists:false}} 的测试聚合查询(这将返回在b 上使用稀疏索引的不完整结果),执行集合扫描:

"winningPlan" : {
    "stage" : "COLLSCAN",
    "filter" : {
        "$not" : {
            "b" : {
                "$exists" : true
            }
        }
    },
    "direction" : "forward"
},

【讨论】:

    猜你喜欢
    • 2018-01-22
    • 1970-01-01
    • 2018-06-12
    • 1970-01-01
    • 2013-06-12
    • 1970-01-01
    • 1970-01-01
    • 2012-07-07
    • 1970-01-01
    相关资源
    最近更新 更多