iT邦幫忙

2021 iThome 鐵人賽

DAY 13
0
Software Development

MongoDB披荊斬棘之路系列 第 13

DAY13 MongoDB 索引(Index) 種類與建立方式

  • 分享至 

  • xImage
  •  

DAY13 MongoDB 索引(Index) 種類與建立方式

什麼是索引(Index)

索引是資料庫設計中非常重要的一環,透過針對特定欄位(一個以上)建立索引,使得任何操作能夠快速找到資料,這也是為什麼操作的查詢條件通常都須建立索引的緣故,所以使用者情境(user scenario)對開發者來說非常重要,如果沒有這些情境,開發者無法預測這個功能該如何使用,進而無法設計出合適的結構或者索引等。

預設索引

MongoDB 內的所有 collection 都有一個 Default Index,打開任一文件都會看到一個 _id 欄位,就是這個。

_id 不需要指定,寫入資料庫時就會自動幫你產生,當然你也可以自己客製化,在某些情境很適合。

索引值排序

MongoDB 索引欄位是有排序的,預設是正序1,反序-1則需要特別設定,至於要使用哪一種排序,需要根據你的使用情境來決定。

通常,跟時間相關都會查詢與現在較近的為主,例如最近一個月的營收、這週的進貨表等等,這樣就很適合使用反序來建立索引。

索引命名

官方的文件載明,建議命名為 [欄位名稱1]_[排序]_[欄位名稱2]_[排序] 這樣的方式。
例如現在有兩個欄位分別叫 ProductId 使用正序,CreateTime 使用倒序,那以此建立的 index 會命名為ProductId_1_CreateTime_-1

  • 索引命名長度為 127 bytes

索引種類與建立

單一欄位索引

顧名思義,使用一個欄位建立的 Index。

以下範例皆使用此 employee 的 collection (僅範例使用,沒考慮設計上問題)

{
  "_id": ObjectId("60a7755055caee86c7479c96"),
  "name": "Aaron",
  "age": 30,
  "department": 1,
  "startWork": 2021-05-21T00:00:00.000+0800
  "address": {
    "city": "taipei",
    "district": "east"
  },
    "assets": [
    {"sn": "PC001", "name":"personal computer"},
    {"sn": "OD001", "name": "office desk"}
  ]
},
{
  "_id": ObjectId("60a7756955caee86c7479c97"),
  "name": "Brad",
  "age": 32,
  "department": 2,
  "startWork": 2021-04-21T00:00:00.000+0800,
  "address": {
    "city": "hsinchu",
    "district": "south"
  },
    "assets": [
    {"sn": "PC002", "name":"personal computer"},
    {"sn": "OD002", "name": "office desk"}
  ]
}

單一欄位建立索引

針對 department 欄位建立索引:

db.employee.createIndex({"department": 1})

巢狀文件欄位索引

Index 也可以建立在 embedded field 上,使用 . 來做階層索引。以 city 為例:

db.employee.createIndex({"address.city": 1})

複合欄位索引

顧名思義是使用兩個以上的欄位組成的索引,在大部分情況都是使用這個的。以上面的範本為例:

db.employee.createIndex({"startWork": -1, "department" : 1})

Multikey欄位索引

Multikey index 是針對欄位是 array 使用的,使用方式如同一般 index 一樣,不需要額外指定它是 multikey。

db.employee.createIndex({"assets.sn" : 1})

文字索引

文字索引,建立一個以上欄位的文字查詢索引。要特別注意的是一個collection只能有一個文字索引

例如要針對 name 欄位建立文字索引,語法稍微不同,如下:

  • Create
db.employee.createIndex({"name" : "text"})
  • Query

查詢時不需指定欄位,需使用 $text $search 語法。

單一字查詢:

db.employee.find({$text : {$search: "aaron"}}})

查詢多個字直接空白隔開即可,例如我要查詢包含 aaron asgard 的名字:

db.employee.find({$text : {$search: "aaron asgard"}}})

查詢包含空格的完整字串:

db.employee.find({$text : {$search: \""aaron asgard\""}}})

還有個反向的功能,例如要排除某一個字,可以使用 - 符號:
搜尋 aaron 但不包含 asgard

db.employee.find({$text : {$search: "aaron -asgard"}}})

取得索引

看完後才發現忘記講如何取得索引,趕緊補上。

db.employee.getIndexes()

刪除索引

db.employee.dropIndex({"index_name"})

索引種類大致上介紹到這邊,明天繼續更深入的內容!


本系列文章會同步發表於我個人的部落格 Pie Note


上一篇
DAY12 MongoDB Facet 與 Bucket 分桶統計
下一篇
DAY14 MongoDB 索引屬性與進階注意事項
系列文
MongoDB披荊斬棘之路30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言