1、索引詳講
一、建立簡單索引
準備數據,建立books文檔並插入200000條數據,以下:
for(var i=0;i<200000;i++){
db.books.insert({number:i,name:i+"book"})
}
1.一、先檢驗一下查詢性能
var start=new Date()
db.books.find({number:65888})
var end=new Date()
end-start
2.二、爲number建立索引
db.books.ensureIndex({number:1})
3.三、再執行第一次查詢的代碼,能夠看出有數量級的性能提高,大概10倍以上。
二、索引使用須要注意的地方
2.一、建立索引的時候,注意1是正序建立索引,-1是倒序建立索引。
2.二、索引的建立,在提升查詢性能的同時,會影響增刪改的性能;
對於常常查詢少插入的文檔能夠考慮用索引。
2.三、符合索引要注意索引的前後順序。
2.四、每一個鍵全創建索引不必定就能提升性能,索引不是萬能的。
2.五、在作排序工做的時候,若是是超大數據量,也能夠考慮加上索引,用來提升排序的性能。
三、索引的名稱
3.一、用VUE查看索引名稱,以下圖:shell
3.二、建立索引同事指定索引的名字
db.books.ensureIndex({name:-1},{name:"bookname"})數據庫
四、惟一索引
4.一、如何解決文檔books不能插入重複的數值
創建惟一索引
db.books.ensureIndex({name:1},{unique:true})
測試
db.books.insert({name:"1book"})
錯誤信息:E11000 duplicate key error index: foorbar.books.$name_1 dup key: { : "1book" }數組
五、過濾重複值
5.一、若是創建惟一索引以前,已經有重複數據,如何處理?
db.books.ensureIndex({name:1},{unique:true,dropDups:true})ide
六、Hint
6.一、如何強制查詢使用指定的索引?
db.books.find({name:"1book",number:1}).hint({name:1})
指定索引必須是已經建立好的索引(包括順序),不然會報以下錯誤:
error: { "$err" : "bad hint", "code" : 10113 }性能
七、explain
7.一、如何詳細查看本次查詢使用哪一個索引和查詢數據的狀態信息
db.books.find({name:"1book"}).explain()
返回結果,以下所示:
> db.books.find({name:"1book"}).explain()
{
"cursor" : "BtreeCursor name_1",
"isMultiKey" : false,
"n" : 1,
"nscannedObjects" : 1,
"nscanned" : 1,
"nscannedObjectsAllPlans" : 1,
"nscannedAllPlans" : 1,
"scanAndOrder" : false,
"indexOnly" : false,
"nYields" : 0,
"nChunkSkips" : 0,
"millis" : 0,
"indexBounds" : {
"name" : [
[
"1book",
"1book"
]
]
},
"server" : "PC-20110917QHJT:27017"
}測試
"cursor" : "BtreeCursor name_1" 使用索引
"nscanned" : 1 查到幾個文檔
"millis" : 0 查詢時間,0是很不錯的性能
2、索引管理
八、system.indexes
8.一、在shell中,查看數據庫已經創建的索引。以下:
db.system.indexes.find()
db.system.namespaces.find()大數據
九、後臺執行
9.一、執行建立索引的過程會暫時鎖表問題,如何解決?
爲了避免影響查詢,咱們可讓索引的建立過程在後臺執行。
db.books.ensureIndex({number:1},{true})
十、刪除索引
10.一、批量和精確刪除索引
db.runCommand({dropIndexes:"books",index:"name_1"}) 精確刪除索引
db.runCommand({dropIndexes:"books",index:"*"}) 批量刪除索引
3、空間索引
十一、mongoDB提供強大的空間索引,能夠查詢出必定範圍的地理座標。示例以下:
準備數據map.txt,以下圖:spa
首先,添加2D索引(默認會創建一個[-180,180]之間的2D索引)
db.map.ensureIndex({"gis":"2d"},{min:-1,max:201})
11.一、查詢出距離點(70,180)最近的3個點
db.map.find({"gis":{$near:[70,180]}},{gis:1,_id:0}).limit(3)//$near操做符表示中心點;若是沒有指定limit,其默認值爲100。
11.二、查詢以點(50,50)和(190,190)爲對角線的正方形中的全部點
var box=[[50,50],[190,190]];//定義一個矩形區域
db.map.find({"gis":{"$within":{"$box":box}}},{gis:1,_id:0})//$box 矩形查找
11.三、查詢出以圓心爲(55,80),半徑爲50,規則下的圓心面積中的點
var center=[55,80];//定義中心點
var radius=50;//定義半徑
db.map.find({"gis":{"$within":{"$center":[center,radius]}}});//$center 圓形查找(注意這裏是數組傳遞)code