1. 程式人生 > >MongoDB索引的種類與使用

MongoDB索引的種類與使用

rop tex 表示 全文索引 數據 spl als 圓形 ear

一:索引的種類

1:_id索引:是絕大多數集合默認建立的索引,對於每個插入的數據,MongoDB都會自動生成一條唯一的_id字段
2:單鍵索引

1.單鍵索引是最普通的索引
2.與_id索引不同,單鍵索引不會自動創建 如:一條記錄,形式為:{x:1,y:2,z:3}
db.imooc_2.getIndexes()//查看索引 
db.imooc_2.ensureIndex({x:1})//創建索引,索引可以重復創建,若創建已經存在的索引,則會直接返回成功。
db.imooc_2.find()//查看數據
技術分享圖片

3:多鍵索引
多鍵索引與單鍵索引創建形式相同,區別在於字段的值。
1)單鍵索引:值為一個單一的值,如字符串,數字或日期。
2)多鍵索引:值具有多個記錄,如數組。

db.imooc_2.insert({x:[1,2,3,4,5]})//插入一條數組數據
技術分享圖片

4:復合索引:查詢多個條件時,建立復合索引
例如{x:1,y:2,z:3}這樣一條數據,要按照x與y的值進行查詢,就需要創建復合索引。

db.imooc_2.ensureIndex({x:1,y:1}) #1升序,-1降序
db.imooc_2.find({x:1,y:2}) #使用復合索引查詢
技術分享圖片

5:過期索引
在一段時間後會過期的索引
在索引過期後,相應的數據會被刪除
適合存儲在一段時間之後會失效的數據,比如用戶的登錄信息、存儲的日誌等。
db.imooc_2.ensureIndex({time:1},{expireAfterSeconds:10}) #創建過期索引,time-字段,expireAfterSeconds在多少秒後過期,單位:秒

db.imooc_2.ensureIndex({time:1},{expireAfterSeconds:30}) #time索引30秒後失效
db.imooc_2.insert({time:new Date()}) #new Date()自動獲取當前時間,ISODate
db.imooc_2.find() #可看到剛才insert的值
技術分享圖片

過30秒後再find,剛才的數據就已經不存在了。

過期索引的限制:
1.存儲在過期索引字段的值必須是指定的時間類型,必須是ISODate或者ISODate數組,不能使用時間戳,否則不能自動刪除。
例如 >db.imooc_2.insert({time:1}),這種是不能被自動刪除的
2.如果指定了ISODate數組,則按照最小的時間進行刪除。
3.過期索引不能是復合索引。因為不能指定兩個過期時間。
4.刪除時間是不精確的。刪除過程是由MongoDB的後臺進程每60s跑一次的,而且刪除也需要一定時間,所以存在誤差

6:全文索引:對字符串與字符串數組創建全文課搜索的索引
不適用全文索引:查找困難,效率低下,需要正則匹配,逐條掃描。
使用全文索引:簡單查詢即可查詢需要的結果

創建方式

db.articles.ensureIndex({key:"text"}) #key-字段名,value-固定字符串text
上述指令表示,在articles這個集合的key字段上創建了一個全文索引

db.articles.ensureIndex({key1:"text",key2:"text"}) #在多個字段上創建全文索引

對於nosql數據庫,每個記錄存儲的key可能都是不同的,如果要在所有的key上建立全文索引,一個一個寫很麻煩,mongodb可以通過下面指令完成:
db.articles.ensureIndex({"$**":"text"}) #給所有字段建立全文索引
技術分享圖片

全文索引的創建:
1:可以為一個字段創建全文索引
2:可以為多個字段創建全文索引
3:可以為集合中所有的字段創建全文索引
註意:上面三種創建全文索引的方式,前兩個方式類似,第三個需要一個特殊的字符串來表示——”$**”,我想如果集合中就兩三個字段,也可以使用2來創建這樣的全文索引,如果這個集合總就一個字段使用1也是可以的,3僅僅是為了統一化而已。

全文索引的查找:
1:使用全文索引查詢不需要指定全文索引的字段名字——直接使用$text,$search即可
2:在MongoDB中每個數據集合只允許創建一個全文索引,不過這個全文索引可以針對一個、多個、全部的數據集合的字段來創建。
3:查詢多個關鍵詞,可以使用空格將多個關鍵詞分開——空格——或的關系
4:指定不包含的字段使用-來表示—— -:非的關系
5:引號包括起來代表與的關系—— \”\”:與的關系

db.articles.find({$text:{$search:"coffee"}})
db.articles.find({$text:{$search:"aa bb cc"}}) #空格代表或操作,aa或bb或cc
db.articles.find({$text:{$search:"aa bb -cc"}}) #-號為非操作,即不包含cc的
db.articles.find({$text:{$search: "\"aa\" \"bb\" \"cc\""}}) #加雙引號可以提供與關系操作
技術分享圖片

相似度查詢:

搜索排序,查詢結果與你查詢條件越相關的越排在前面。
MongoDB中可以使用$meta操作符完成,格式:

{score:{$meta: "textScore"}}
技術分享圖片

在全文搜索的格式中加入這樣一個條件,如下:

db.imooc_2.find({$text:{$search:"aa bb"}},{score:{$meta:"textScore"}})
技術分享圖片

搜索出的結果會多出一個score字段,這個得分越高,相關度越高。
還可以對查詢出的結果根據得分進行排序:

db.imooc_2.find({$text:{$search:"aa bb"}},{score:{$meta:"textScore"}}).sort({score:{$meta:"textScore"}})
技術分享圖片

加上.sort方法即可。

全局索引的限制:
1.每次查詢,只能指定一個$text查詢
2.$text查詢不能出現在$nor查詢中
3. 查詢中如果包含了$text, hint不再起作用(強制指定索引hint)
4. MongoDB全文索引還不支持中文

7:地理位置索引
將一些點的位置存儲在MongoDB中,創建索引後,可以按照位置來查找其他點。

地理位置索引分為兩類:
1.2D索引,用於存儲和查找平面上的點。
2.2Dsphere索引,用於存儲和查找球面上的點。
例如:
查找距離某個點一定距離內的點。
查找包含在某區域內的點。

分為2種:2D平面地理位置索引 和 2D sphere 2D球面地裏位置索引 2者的區別在於計算距離時使用的計算方式不同(平面距離還是球面距離)

2D地理位置索引創建方式

db.collection.ensureIndex({w:”2d”})

2D地理位置索引的取值範圍以及表示方法 經緯度[經度,緯度]
經緯度取值範圍 經度[-180,180] 緯度[-90,90]

db.collection.insert({w:[180,90]})
技術分享圖片

2D地理位置查詢有2種
1.使用$near 查詢距離某個點最近的點 ,默認返回最近的100個點

db.collection.find({w:{$near:[x,y]}})
技術分享圖片

可以使用$maxDistance:x 限制返回的最遠距離

db.collection.find({w:{$near:[x,y],$maxDistance:z}})
技術分享圖片

2.使用$geoWithin 查詢某個形狀內的點
形狀的表示方式:

1. $box 矩形,使用{$box:[[x1,y1],[x2,y2]]}
2. $center 圓形,使用 {$center:[[x,y],r]}
3. $polygon 多邊形,使用 {$polygon:[[x1,y1],[x2,y2],[x3,y3]]}
技術分享圖片

mongodb geoWithin 查詢

查詢矩形中的點
db.collection.find({w:{$geoWithin:{$box:[[0,0],[3,3]]}}})
查詢圓中的點
db.collection.find({w:{$geoWithin:{$center:[[0,0],5]}}})
查詢多邊形中的點
db.collection.find({w:{$geoWithin:{$polygon:[[0,0],[0,1],[2,5],[6,1]]}}})
技術分享圖片

mongodb geoNear 查詢

geoNear 使用 runCommand命令操作
db.runCommand({
geoNear:"collection名稱",
near:[x, y],
minDistance:10(對2d索引無效,對2Dsphere有效‘)
maxDistance:10
num:1 返回數量
})
技術分享圖片

可返回最大距離和平均距離等數據.

返回的數據:
results:查詢到的數據;dis:距離,obj:數據記錄
stats:查詢參數,maxDistance最大距離和avgDistance平均距離
ok:1,查詢成功

mongodb 2Dsphere索引詳解

2Dsphere index create method
use command:

db.collection.ensureindex({key: ‘2dsphere‘})
技術分享圖片

2Dsphere位置表示方式:
GeoJSON:描述一個點,一條直線,多邊形等形狀。
格式:

{type:‘‘, coordinates:[list]}
技術分享圖片

GeoJSON查詢可支持多邊形交叉點等,支持MaxDistance 和 MinDistance

索引屬性

創建索引的格式:

db.collection.ensureIndex({indexValue},{indexProperty})
技術分享圖片

其中:indexProperty比較重要的有
1:名字

db.collection.ensureIndex({indexValue},{name:})
技術分享圖片

MongoDB會自動的創建,規則是key_1 或者 key_-1 1或者-1代表排序方向,一般影響不大,長度一般有限制125字節
為了見名知意我們可以自己來命名

自定義索引名稱方式:

db.imooc_2.ensureIndex({x:1,y:1,z:1,m:1},{name:"normal_index"})
技術分享圖片

刪除索引

db.imooc_dropIndex(indexName)
技術分享圖片

刪除索引時,可以通過我們定義的名字來刪除索引

db.imooc_2.dropIndex("normal_index")
技術分享圖片

2:唯一性:不允許在同一個集合上插入具有同一唯一性的數據。

db.imooc_2.ensureIndex({x:1,y:1,z:1,m:1},{unigue:true)
技術分享圖片

3:稀疏性

db.collection.ensureIndex({},{sparse:true/false}) #指定索引是否稀疏
技術分享圖片

MongoDB索引默認是不稀疏的。
稀疏性的不同代表了MongoDB在處理索引中存在但是文檔中不存在的字段的兩種不同的方法。
例如,我們為一個collection的x字段指定了索引,但這個collection中可以插入如{y:1,z:1}這種不存在x字段的數據,
如果索引為不稀疏的,mongodb依然會為這個數據創建索引,如果在創建索引時指定為稀疏索引,那麽就可以避免這件事情發生了。

db.imooc_2.insert({"m":1})
db.imooc_2.insert({"n":1})
技術分享圖片

通過$exists可以判斷字段是否存在,如

db.imooc_2.find({m:{$exists:true}}) #篩選出有m字段的文檔
技術分享圖片

給這個文檔的m字段創建一個稀疏索引:

db.imooc_2.ensureIndex({m:1},{sparse:true})
技術分享圖片

第二條文檔不存在m字段,所以不會創建這個索引
如果使用稀疏索引查找不存在稀疏索引字段的文檔,mongodb則不會使用這個索引查找
例如:

db.imooc_2.find({m:{$exists:false}}) #可以查到數據
技術分享圖片

但如果我們通過hint強制使用索引,就不會查到數據了

db.imooc_2.find({m:{$exists:false}}).hint("m_1") #查不出數據,因為n上並沒有m字段的索引
技術分享圖片

4:是否定時刪除(過期索引TTL)

--------------------- 本文來自 DoNotStop 的CSDN 博客 ,全文地址請點擊:https://blog.csdn.net/u013725455/article/details/52037897?utm_source=copy

MongoDB索引的種類與使用