千家信息网

MongoDB的索引

发表于:2025-11-07 作者:千家信息网编辑
千家信息网最后更新 2025年11月07日,1、简介它就像是一本书的目录,如果没有它,我们就需要对整个书籍进行查找来获取需要的结果,即所说的全盘扫描;而有了目录(索引)之后就可以通过它帮我们定位到目标所在的位置,快速的获取我们想要的结果。2、演
千家信息网最后更新 2025年11月07日MongoDB的索引

1、简介

它就像是一本书的目录,如果没有它,我们就需要对整个书籍进行查找来获取需要的结果,即所说的全盘扫描;

而有了目录(索引)之后就可以通过它帮我们定位到目标所在的位置,快速的获取我们想要的结果。

2、演示

第一步,向用户集合users中插入100W条数据

 1 var insertUsers = function() { 2     var start = new Date().getTime(); 3     for (var i = 1; i <= 1000000; i++) { 4         db.users.insert({ 5             "userid": i, 6             "username": "wjg" + i, 7             "age": Math.floor(Math.random() * 100), //年龄为0~99的随机整数 8             "createdate": new Date() 9         })10     }11     var end = new Date().getTime();12     print("插入100W条数据共耗时" + (end - start) / 1000 + "秒");13 }

LZ的渣渣I3和4G内存总共耗时了484.623秒,约8分多钟。任务管理器里边可以很清楚的看到当时CPU、内存和磁盘使用率都普遍的增高。

第二步:查询用户名为"wjg465413"的文档对象

View Code

说明:这里的explain方法相当于查询计划,它会返回给你查询过程的详细信息。它的参数有三种模式:"queryPlanner"(查询计划[默认])、"executionStats"(执行状态)和"allPlansExecution"(所有执行计划),这里我们只关注它返回给我们的以下几个信息。

1 "executionTimeMillis" : 865  //执行的毫秒数 注:如果你是第一次执行,可能会花费更长的时间2 3 "totalDocsExamined" : 1000000  //共检查的文档数

第三步:在用户名"username"字段上加上索引

1 db.users.createIndex({ "username" : 1 })

重新执行上次的查询操作

View Code

可以看到两次的查询计划有很大的差别,我们还是着重看下那两个属性值。

1 "executionTimeMillis" : 53  //执行的毫秒数2 3 "totalDocsExamined" : 1  //共检查的文档数

加过索引之后查询这个文档所耗费的时间仅仅为53毫秒,并且扫描一次直接定位,性能提升了16倍。可见合理使用索引的重要性!

注:"_id"字段是Mongo为我们默认添加的索引,而且是唯一索引,保证了数据的唯一性,不可以移除。另外,使用limit(1)限制查询结果的数量也可以提高查询速度

3、索引的类型

a)、单一索引:可以在数据集上任意一个字段上建立索引,包括普通的属性键、内嵌文档以及内嵌文档中的属性键。

db.users.createIndex({ "username" : 1 })    //普通属性键的索引//假设class是一个内嵌的文档db.users.createIndex({ "class" : 1 })    //内嵌文档的索引 db.users.createIndex({ "class.classname" : 1 })    //内嵌文档中的属性键索引

索引方向:1表示升序,-1表示降序

b)、复合索引:以多个属性键为基础而建立得索引

1 db.users.createIndex({ "username" : 1, "age" : -1, "userid" : 1 })    //在"username"、"age"和"userid"上建立复合索引

索引前缀:通过建立上边的复合索引之后,Mongo就相当于同时拥有了三个索引一样,分别是{"username" : 1},{"username" : 1, "age" : -1}和{"username" : 1, "age" : -1, "userid" : 1},但是像{"age" : -1},{"userid" : 1}或者{"age" : -1, "userid" : 1}这三个索引并不会起作用。所以它会使用包含了前缀(首个)的索引的作为复合索引

c)、多键索引:为数组中的多个值建立索引以实现高效查询。

注:Ⅰ、不允许在多个数组上建立复合索引

  Ⅱ、不能指定片键作为多键索引

  Ⅲ、哈希索引不能是多键

  Ⅳ、多键索引不支持覆盖查询

d)、地理空间索引和查询:Mongo提供了两种曲面类型的索引:2dsphere索引和2d索引。查询类型包括:包含(inclusion),交叉(intersection)和接近(proximity)

e)、文本索引:用来支持查询包含了字符串或者字符串数组的文档

1 db.users.createIndex({"username" : "text"})

注:文本索引不支持排序并且一个复合文本索引不能再包含其他任何索引了

f)、哈希索引:它可以在使用了哈希片键进行分片的数据集上进行索引,支持相等查询,但是不支持范围查询

1 db.users.createIndex({"username" : "hashed"})

4、索引特性

a)、TTL(Time-To-Live)索引:是一种具有生命周期的索引,它允许为每一个文档设置一个超时时间

1 db.users.createIndex({ "createdate" : 1 },{ "expireAfterSecs" : 60*60*24 })

说明:在"createdate"字段上建立一个TTL索引,当这个自段存在并且是日期类型,当服务器时间比"createdate"字段的时间晚60*60*24秒,即24小时时,文档就会被删除

b)、唯一索引:确保集合的每一个文档的指定键都有唯一值

1 db.users.createIndex({"username" : 1}, {"unique" : true})

c)、稀疏索引:Mongo里边的null会被看做值,如果有一个可能存在也可能不存在的字段,我们可以使用稀疏索引

1 db.users.createIndex({"age" : 1},{"sparse" : true})

4、索引操作

a)、查看所有索引

1 db.users.getIndexes()

b)、移除索引

1 db.users.dropIndex({"createdate1" : 1 })

c)、移除所有索引

1 db.users.dropIndexes()

d)、重建索引

1 db.users.reIndex()

说明:该操作会先删除所有索引,包括"_id",然后重新创建所有索引

服务、思考、安全


索引 查询 文档 字段 属性 数据 时间 支持 类型 多个 数组 文本 结果 哈希 普通 稀疏 三个 信息 内存 前缀 数据库的安全要保护哪些东西 数据库安全各自的含义是什么 生产安全数据库录入 数据库的安全性及管理 数据库安全策略包含哪些 海淀数据库安全审计系统 建立农村房屋安全信息数据库 易用的数据库客户端支持安全管理 连接数据库失败ssl安全错误 数据库的锁怎样保障安全 面试官问你网络安全是怎么做的 phpcms数据库位置 网络安全知识教育观后感 北京云腾在线网络技术 Java开发数据库技术培训课程 天津水性软件开发试验设备 豫教思语网络安全知识竞赛 深圳程序软件开发靠谱吗 江苏软件开发团队 数据库约束的特征 芯片上的软件开发 通信网络及计算机网络技术 电脑网络安全证书错误怎么办 怀旧服服务器怎么设置隐藏房间 华中科技大学互联网的牛人 黄石市网络安全宣传 学c 有什么软件开发 2000数据库太大 磊科路由虚拟服务器设置 高拍仪直接传送到服务器 饥荒联机版服务器的mod修改 温州职高计算机网络技术报名 梦幻西游手游再续前缘服务器在哪 阿里巴巴聊天软件开发 怀旧服服务器怎么设置隐藏房间 数据库编写用什么技术 软件开发公司的绩效考核指标 钉钉服务器型号 网狐棋盘那个是服务器协调软件 新戴尔720服务器如何设置
0