关于MongoDB数据库中索引的简介

  介绍

这篇文章主要介绍关于MongoDB数据库中索引的简介,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!

当你抱怨MongoDB集合查询效率低的时候,可能你就需要考虑使用索引了,为了方便后续介绍,先科普下MongoDB里的索引机制(同样适用于其他的数据库比如mysql)。

mongo - 9552: PRIMARY& gt;, db.person.find ()   {,“_id",:, ObjectId (“571 b5da31b0d530a03b3ce82"),“name",:,“jack",,“age",:, 19,}   {,“_id",:, ObjectId (“571 b5dae1b0d530a03b3ce83"),“name",:,“rose",,“age",:, 20,}   {,“_id",:, ObjectId (“571 b5db81b0d530a03b3ce84"),“name",:,“jack",,“age",:, 18,}   {,“_id",:, ObjectId (“571 b5dc21b0d530a03b3ce85"),“name",:,“tony",,“age",:, 21,}   {,“_id",:, ObjectId (“571 b5dc21b0d530a03b3ce86"),“name",:,“adam",,“age",:, 18,}

当你往某各个集合插入多个文档后,每个文档在经过底层的存储引擎持久化后,会有一个位置信息,通过这个位置信息,就能从存储引擎里读出该文档。比如mmapv1引擎里,位置信息是“文件id +文件内抵消”,在wiredtiger存储引擎(一个KV存储引擎)里,位置信息是wiredtiger在存储文档时生成的一个关键,通过这个键能访问到对应的文档;为方便介绍,统一用pos(位置的缩写)来代表位置信息。

比如上面的例子里,人集合里包含插入了4个文档,假设其存储后位置信息如下(为方便描述,文档省去_id字段)

关于MongoDB数据库中索引的简介

假设现在有个查询db.person。找到({年龄:18}),查询所有年龄为18岁的人,这时需要遍历所有的文档(“全表扫描”),根据位置信息读出文档,对年龄比字段是否为18岁。当然如果只有4个文档,全表扫描的开销并不大,但如果集合文档数量到百万,甚至千万上亿的时候,对集合进行全表扫描开销是非常大的,一个查询耗费数十秒甚至几分钟都有可能。

如果想加速db.person。找到({年龄:18}),就可以考虑对表人的年龄字段建立索引。

db.person.createIndex(,{年龄:1},),,//,按年龄字段创建升序索引

建立索引后,MongoDB会额外存储一份按年龄字段升序排序的索引数据,索引结构类似如下,索引通常采用类似btree的结构持久化存储,以保证从索引里快速(O (logN)的时间复杂度)找出某个年龄值对应的位置信息,然后根据位置信息就能读取出对应的文档。

关于MongoDB数据库中索引的简介

简单的说,索引就是将文档按照某个(或某些)字段顺序组织起来,以便能根据该字段高效的查询。有了索引,至少能优化如下场景的效率:

查询,比如查询年龄为18的所有人

更新/删除,将年龄为18的所有人的信息更新或删除,因为更新或删除时,需要根据条件先查询出所有符合条件的文档,所以本质上还是在优化查询

排序,将所有人的信息按年龄排序,如果没有索引,需要全表扫描文档,然后再对扫描的结果进行排序

众所周知,MongoDB默认会为插入的文档生成_id字段(如果应用本身没有指定该字段),_id是文档唯一的标识,为了保证能根据文档id快递查询文档,MongoDB默认会为集合创建_id字段的索引。

mongo - 9552: PRIMARY& gt;, db.person.getIndexes(),//,查询集合的索引信息   (   ,,,{   ,,,,,,,“ns",:,“test.person",,,//,集合名   ,,,,,,,“v",, 1,,,,,,,,,,,,,,,,//,索引版本   ,,,,,,,“key",:,{,,,,,,,,,,,,,//,索引的字段及排序方向   ,,,,,,,,,,,“_id",, 1,,,,,,,,,,,//,根据_id字段升序索引   ,,,,,,,},   ,,,,,,,“name",:,“_id_",,,,,,,,//,索引的名称   ,,,}   )

MongoDB支持多种类型的索引,包括单字段索引,复合索引,多关键索引,文本索引等,每种类型的索引有不同的使用场合。

db.person.createIndex(,{年龄:1},)

上述语句针对年龄创建了单字段索引,其能加速对年龄字段的各种查询请求,是最常见的索引形式,MongoDB默认创建的id索引也是这种类型。

{年龄:1}代表升序索引,也可以通过{年龄:1}来指定降序索引,对于单字段索引,升序/降序效果是一样的。

复合索引是单一的字段索引的升级版本,它针对多个字段联合创建索引,先按第一个字段排序,第一个字段相同的文档按第二个字段排序,依次类推,如下针对年龄、姓名这2个字段创建一个复合索引。

关于MongoDB数据库中索引的简介