日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

聊一聊mongodb中的 explain 和 hint

發(fā)布時(shí)間:2023/12/4 编程问答 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 聊一聊mongodb中的 explain 和 hint 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

看到explain和hint的時(shí)候,第一個(gè)想到的就是mysql,確實(shí),這就是在mysql中借鑒過來的,既然是借鑒過來的,我想大家都知道這兩個(gè)關(guān)鍵字的用處,話不多說,速速觀看~~~

一:explain演示

1. 構(gòu)建數(shù)據(jù)

為了方便演示,我需要生成10條數(shù)據(jù) to inventory,而且還是要在 no index 的情況下,比如下面這樣:

db.inventory.insertMany([ {?"_id"?:?1,?"item"?:?"f1",?type:?"food",?quantity:?500?}, {?"_id"?:?2,?"item"?:?"f2",?type:?"food",?quantity:?100?}, {?"_id"?:?3,?"item"?:?"p1",?type:?"paper",?quantity:?200?}, {?"_id"?:?4,?"item"?:?"p2",?type:?"paper",?quantity:?150?}, {?"_id"?:?5,?"item"?:?"f3",?type:?"food",?quantity:?300?}, {?"_id"?:?6,?"item"?:?"t1",?type:?"toys",?quantity:?500?}, {?"_id"?:?7,?"item"?:?"a1",?type:?"apparel",?quantity:?250?}, {?"_id"?:?8,?"item"?:?"a2",?type:?"apparel",?quantity:?400?}, {?"_id"?:?9,?"item"?:?"t2",?type:?"toys",?quantity:?50?}, {?"_id"?:?10,?"item"?:?"f4",?type:?"food",?quantity:?75?}]);

2. 無索引查詢

db.inventory.find({?quantity:?{?$gte:?100,?$lte:?200?}?} ).explain("executionStats")

從上圖中可以看到三個(gè)圈圈,這些都是我們在find中非常重要的信息,具體信息解釋如下:

1) COLLSCAN

這個(gè)是什么意思呢?如果你仔細(xì)一看,應(yīng)該知道就是CollectionScan,這就是所謂的“集合掃描”,對不對,看到集合掃描是不是就可以直接map到數(shù)據(jù)庫中的table scan/heap scan呢???是的,這就是所謂的性能最爛最無奈的由來。

2) nReturned

這個(gè)很簡單,就是說最后返回的num個(gè)數(shù),從圖中可以看到最終返回了三條。。。

3) docsExamined

那這個(gè)是什么意思呢??其實(shí)就是檢查了10個(gè)documents。。。最后返回了上面的nReturned。。。

ok,從上面三個(gè)信息中可以得出,原來我 examine 10 條數(shù)據(jù),最終才返回3條,說明7條數(shù)據(jù)的scan是無用的,問題就來了,如何減少examine的documents次數(shù)。。。完整的plans如下:

/*?1?*/ {"queryPlanner"?:?{"plannerVersion"?:?1,"namespace"?:?"datamip.inventory","indexFilterSet"?:?false,"parsedQuery"?:?{"$and"?:?[?{"quantity"?:?{"$lte"?:?200.0}},?{"quantity"?:?{"$gte"?:?100.0}}]},"winningPlan"?:?{"stage"?:?"COLLSCAN","filter"?:?{"$and"?:?[?{"quantity"?:?{"$lte"?:?200.0}},?{"quantity"?:?{"$gte"?:?100.0}}]},"direction"?:?"forward"},"rejectedPlans"?:?[]},"executionStats"?:?{"executionSuccess"?:?true,"nReturned"?:?3,"executionTimeMillis"?:?1,"totalKeysExamined"?:?0,"totalDocsExamined"?:?10,"executionStages"?:?{"stage"?:?"COLLSCAN","filter"?:?{"$and"?:?[?{"quantity"?:?{"$lte"?:?200.0}},?{"quantity"?:?{"$gte"?:?100.0}}]},"nReturned"?:?3,"executionTimeMillisEstimate"?:?0,"works"?:?12,"advanced"?:?3,"needTime"?:?8,"needYield"?:?0,"saveState"?:?0,"restoreState"?:?0,"isEOF"?:?1,"invalidates"?:?0,"direction"?:?"forward","docsExamined"?:?10}},"serverInfo"?:?{"host"?:?"localhost.localdomain","port"?:?27017,"version"?:?"3.2.8","gitVersion"?:?"ed70e33130c977bda0024c125b56d159573dbaf0"},"ok"?:?1.0 }

3. 使用 single field 加速查找

知道前因后果之后,就可以進(jìn)行針對性的建立索引,比如拿 quality 字段舉例如下:

db.inventory.createIndex({?quantity:?1})db.inventory.find({?quantity:?{?$gte:?100,?$lte:?200?}?} ).explain("executionStats")

這時(shí)候有意思了,當(dāng)執(zhí)行完 createindex 之后,再次 explain,有4個(gè)重要的parameters需要特別注意一下:

1) IXSCAN

這個(gè)時(shí)候再也不是所謂的COLLSCAN了,而是IndexScan,說明已經(jīng)命中索引了。

2) nReturned,totalDocsExamined,totalKeysExamined

從圖中可以看到三個(gè)參數(shù)都是3,這就說明 mongodb 查看了3個(gè)key,3個(gè)document,返回了3個(gè)文檔,這就是所謂的高性能吧。

二:hint演示

說到hint,也挺有意思,它用來強(qiáng)制mongodb 執(zhí)行指定的索引,為了方便演示,做兩組復(fù)合索引,比如這次在quality和type上構(gòu)建一下:

構(gòu)建完之后,我強(qiáng)制 mongodb 去使用 quantity 開頭的復(fù)合索引,從而強(qiáng)制mongodb 放棄那個(gè)以{type:1,quantity:1}的復(fù)合索引,很有意思哦,比如下圖:

從圖中可以看到,mongodb 檢查了6個(gè)keys最終找到了2個(gè)文檔,下面我不hint來看一下mongodb自己抉擇的最優(yōu)plan是怎么樣的。

再看上面的圖,你應(yīng)該明白了,mongodb果然執(zhí)行了那個(gè)最優(yōu)的plan,是不是很好玩,好了,本篇就說到這里,希望對你有幫助~

總結(jié)

以上是生活随笔為你收集整理的聊一聊mongodb中的 explain 和 hint的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。