MongoDB基礎教程系列--第六篇 MongoDB 索引
https://www.cnblogs.com/liruihuan/p/6682575.html
使用索引可以大大提高文件的查詢效率。如果沒有索引,會遍歷集合中所有文件,才能找到匹配查詢語句的文件。這樣遍歷集合中整個文件的方式是非常耗時的,特別是處理大資料時,耗時幾十秒甚至幾分鐘都是有可能的。
建立索引
MongoDB 中,使用 ensureIndex() 方法建立索引。
格式
1 |
|
其中,KEY表示要建立索引的欄位名稱,1 表示按升序排列欄位值。-1 表示按降序排列。
範例
1、給 user 集合中 name 欄位新增索引
1 2 |
|
MongoDB 中用 db.collection.getIndexes() 方法查詢集合中所有的索引,我們查詢一下 user 中所有的索引。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
{
"_id" : 1
|
我們發現 user 中有兩個索引,其中索引 "_id_" 是我們建立 user 集合時,MongoDB 自動生成的索引。第二個索引就是我們剛才建立的索引,其中,name 值"name_1"表示索引名稱,MongoDB 會自動生成的索引名稱。當然,我們也可以自己指定索引的名稱。
2、給 user 集合中 age 欄位新增索引,並指定索引名稱為 "index_age_esc"。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
|
指定索引名稱用到的 name 引數,只是 ensureIndex() 方法可接收可選引數的其中一個,下表列出了 ensureIndex() 方法可接收的引數
Parameter | Type | Description |
---|---|---|
background | 布林值 | 建索引過程會阻塞其它資料庫操作,background可指定以後臺方式建立索引,即增加 "background" 可選引數。 "background" 預設值為false。 |
unique | 布林值 | 建立的索引是否唯一。指定為true建立唯一索引。預設值為false. |
name | 字串 | 索引的名稱。如果未指定,MongoDB的通過連線索引的欄位名和排序順序生成一個索引名稱。 |
dropDups | 布林值 | 在建立唯一索引時是否刪除重複記錄,指定 true 建立唯一索引。預設值為 false. |
sparse | 布林值 | 對文件中不存在的欄位資料不啟用索引;這個引數需要特別注意,如果設定為true的話,在索引欄位中不會查詢出不包含對應欄位的文件.。預設值為 false. |
expireAfterSeconds | 整型 | 指定一個以秒為單位的數值,完成 TTL設定,設定集合的生存時間。 |
v | 索引版本 | 索引的版本號。預設的索引版本取決於mongod建立索引時執行的版本。 |
weights | 文件(document) | 索引權重值,數值在 1 到 99,999 之間,表示該索引相對於其他索引欄位的得分權重。 |
default_language | 字串 | 對於文字索引,該引數決定了停用詞及詞幹和詞器的規則的列表。 預設為英語 |
language_override | 字串 | 對於文字索引,該引數指定了包含在文件中的欄位名,語言覆蓋預設的language,預設值為 language. |
唯一索引
MongoDB和關係型資料庫一樣都可以建立唯一索引,重複的鍵值就不能重新插入了,MongoDB 用 unigue 來確定建立的索引是否為唯一索引,true 表示為唯一索引,下面給 user 集合的 name 欄位指定唯一索引
1 2 3 4 5 6 7 |
|
可以看出,建立了唯一索引的欄位,是不能再插入 "liruihuan" 的 name 值的。
複合索引
ensureIndex() 方法中你也可以設定使用多個欄位建立索引
範例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
|
刪除索引
MongoDB 用dropIndex() 方法刪除索引
格式
1 |
|
注:dropIndex() 方法可根據指定的索引名稱或索引文件刪除索引(_id上的預設索引除外)
範例
我們用兩種方式刪除掉 user 中 name 欄位上的索引
1 2 |
|
還可以用 dropIndexes() 刪除集合中所有索引(_id上的預設索引除外)
1 |
|
查詢分析
查詢分析是查詢語句效能分析的重要工具。
MongoDB 中查詢分析用 explain() 和 hint() 方法
範例
我們向集合 user 中插入20萬條資料,利用 explain() 查詢建立索引前後,執行時間的比較,來看看建立索引對查詢效率的提高程度。
第一步,向 user 中插入20萬條資料
1 2 |
|
第二步,刪除 user 集合中欄位 name 上的索引,然後查詢 name = "lrh100000",利用explain("executionStats")查詢此時執行的時間。說明:MongoDB explain() 方法在3.0以後版本中發生了很大改變,3.0之前版本直接用explain()就可以,不用傳引數,如果想詳細瞭解,請訪問官網。
1 2 3 4 5 6 7 8 9 10 11 |
|
explain.executionStats.executionTimeMillis:表示查詢所用的時間,單位是毫秒。
我們可以清楚的看出,沒用索引查詢用到的時間是 109 毫秒。
第三步,給 user 集合中 name 欄位新增索引,然後再查詢同一個條件,看執行查詢所用了多久時間。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
|
如果用到了索引,explain() 方法會返回 winningPlan,標識用到的索引名稱 indexName
我們可以清楚到處,用了索引,執行時間只有 1 毫秒,可以看出,查詢效率的提高可不是一星半點。
注:如果想更詳細的瞭解 explain() 返回的引數,可以去官網看一下
第四步,這一步我們重點看看 hint() 方法的用法。hint() 方法用來強制 MongoDB 使用一個指定的索引。
我們給 user 再新增一個 {"name":1, "age":1},利用 explain() 方法,看一下用到了哪個索引。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
|
可以看出,此時用到的索引是 "name_1_age_1",如果我們想用索引 "name_1",就可以用 hint() 方法指定。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
|