[MongoDB] aggregate 查詢的優化思路


 

首先從業務角度出發,不必要的篩選條件和粗略的篩選條件會嚴重影響查詢速度,比如 $or 查詢和 $in 查詢,視情況盡可能去掉。 

 

程序中打印出查詢條件的各部分,有 $match、$group。比如 PHP 中可以通過 var_export()。

由於 aggregate 執行主要是 pipeline 步驟,所以着重需要關注的是 $match 條件。

 

打印出的數組 json_encode 后可以在 Robo3T 等客戶端中作為 aggregate 的條件使用。

關於 aggregate 查詢條件的格式,可參考:https://studio3t.com/knowledge-base/articles/build-mongodb-aggregation-queries/

為了方便查看 json 條件格式,可以對json在線格式化,之后使用如 Example1.

 

aggregate() 后面直接帶不了 explain() 方法,為了使用 explain() 方法查看索引使用情況等信息,復制出 $match 的 json 條件 到 find({ }) 中,然后帶上 explain() 方法。

查看 explain() 顯示的信息 queryPlanner 部分,里面有 winningPlan.stage 狀態分析,如 Example2.

常見的 winningPlan.stage 如下:
  COLLSCAN:全表掃描
  IXSCAN      :索引掃描
  FETCH       :根據索引去檢索指定document
  更多的可以搜索 mongodb explain 相關信息。

 

把 COLLSCAN 優化成  IXSCAN 使用索引,此時再看 winningPlan.inputStage.keyPattern 使用的索引字段是哪個。

如果 keyPattern 使用的是低效率的索引可以通過 hint 用法強制指定索引,支持普通查詢和聚合查詢。

普通查詢的 hint 方法: ->find({})->hint({ diff_id: 1 })

聚合查詢的 hint 參數:docs.mongodb.com,如 Example3.

 

Example1.

db.getCollection('diff_detail').aggregate(
[
    {
    "$match": {
        "diff_id": ObjectId('71162dcf17a1f594edcc69bc'),
        "pvalue": {
            "$lt": 0.05
        },
        "vip": {
            "$gt": 1
        },
        "$or": [{
            "fc": {
                "$gt": 1
            }
        }, {
            "fc": {
                "$lt": 1
            }
        }],
        "diff_group": {
            "$in": ["a1_vs_A1", "a2_vs_A2", "a3_vs_A3", "a4_vs_A4", "a5_vs_A5"]
        }
    }
    },
    {
    "$group": {
        "_id": {
            "table_type": "$table_type",
            "diff_group": "$diff_group"
        },
        "count": {
            "$sum": 1
        }
    }
    }
]

);

 

Example2.

{
    "queryPlanner" : {
        "plannerVersion" : 1,
        "namespace" : "xxxdb.diff_detail",
        "indexFilterSet" : false,
        "parsedQuery" : {
            "$and" : [ 
                {
                    "$or" : [ 
                        {
                            "fc" : {
                                "$lt" : 1.0
                            }
                        }, 
                        {
                            "fc" : {
                                "$gt" : 1.0
                            }
                        }
                    ]
                }, 
                {
                    "diff_id" : {
                        "$eq" : ObjectId("71162dcf17a1f594edcc69bc")
                    }
                }, 
                {
                    "pvalue" : {
                        "$lt" : 0.05
                    }
                }, 
                {
                    "vip" : {
                        "$gt" : 1.0
                    }
                }, 
                {
                    "diff_group" : {
                        "$in" : [ 
                            "a1_vs_A1", 
                            "a2_vs_A2", 
                            "a3_vs_A3", 
                            "a4_vs_A4", 
                            "a5_vs_A5"
                        ]
                    }
                }
            ]
        },
        "queryHash" : "22D09A47",
        "planCacheKey" : "22D09A47",
        "winningPlan" : {
            "stage" : "COLLSCAN",
            "filter" : {
                "$and" : [ 
                    {
                        "$or" : [ 
                            {
                                "fc" : {
                                    "$lt" : 1.0
                                }
                            }, 
                            {
                                "fc" : {
                                    "$gt" : 1.0
                                }
                            }
                        ]
                    }, 
                    {
                        "diff_id" : {
                            "$eq" : ObjectId("71162dcf17a1f594edcc69bc")
                        }
                    }, 
                    {
                        "pvalue" : {
                            "$lt" : 0.05
                        }
                    }, 
                    {
                        "vip" : {
                            "$gt" : 1.0
                        }
                    }, 
                    {
                        "diff_group" : {
                            "$in" : [ 
                                "a1_vs_A1", 
                                "a2_vs_A2", 
                                "a3_vs_A3", 
                                "a4_vs_A4", 
                                "a5_vs_A5"
                            ]
                        }
                    }
                ]
            },
            "direction" : "forward"
        },
        "rejectedPlans" : []
    },
    "serverInfo" : {
        "host" : "mongodb446",
        "port" : 27017,
        "version" : "4.4.1",
        "gitVersion" : "ad91a93a5a31e175f5cbf8c69561e788bbc55ce1"
    },
    "ok" : 1.0
}

 

Example3.

 

Refer:MongoDB適用場景

Link:https://www.cnblogs.com/farwish/p/15379066.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM