1. $运算符如何使用索引
1.1 低效的运算符

$ne、$not查询可以使用索引,但不是很有效,尽量避免

1.2 范围查询

范围查询其实是多值查询,根据复核索引规则,尽可能先等值精确匹配,然后范围查询

1.3 OR查询

$or实际执行两个索引查询然后合并,应尽可能使用$in,而非$or

2. 索引对象和数组
2.1 索引内嵌文档
db.getCollection('users').createIndex({'loc.city': 1})
2.2 索引数组
db.getCollection('blog').createIndex({'comments.date': 1})

对数组索引就是对数组的每个元素创建索引项,代价比较高,尽量避免使用

2.3 多键索引

如果一个文档有被索引的数组字段,则该索引被标记为多键索引,恢复非多键索引只能删除索引重建

2.4 索引基数

基数是指集合中某个字段有多少个不通的值。根据经验来讲,应该把基数比较高的键放在复核索引的前面,比如对username在前,gender在后

3. explain输出详解
db.getCollection('users').find({'age': 42}).explain('executionStats')
{
"queryPlanner": {
"plannerVersion": NumberInt("1"),
// 集合名称
"namespace": "study.users",
"indexFilterSet": false,
"parsedQuery": {
"age": {
"$eq": 42
}
},
// 获胜执行计划
"winningPlan": {
"stage": "FETCH",
"inputStage": {
"stage": "IXSCAN",
"keyPattern": {
"age": 1,
"username": 1
},
// 索引名称
"indexName": "age_1_username_1",
// 是否使用多键索引
"isMultiKey": false,
"multiKeyPaths": {
"age": [ ],
"username": [ ]
},
"isUnique": false,
"isSparse": false,
"isPartial": false,
"indexVersion": NumberInt("2"),
"direction": "forward",
"indexBounds": {
"age": [
"[42.0, 42.0]"
],
"username": [
"[MinKey, MaxKey]"
]
}
}
},
"rejectedPlans": [ ]
},
"executionStats": {
"executionSuccess": true,
// 实际返回的文档数
"nReturned": NumberInt("8321"),
// 查询计划花费的总运行时间
"executionTimeMillis": NumberInt("465"),
// 扫描的索引项数量
"totalKeysExamined": NumberInt("8321"),
// 扫描的文档数
"totalDocsExamined": NumberInt("8321"),
"executionStages": {
"stage": "FETCH",
"nReturned": NumberInt("8321"),
"executionTimeMillisEstimate": NumberInt("207"),
"works": NumberInt("8322"),
"advanced": NumberInt("8321"),
"needTime": NumberInt("0"),
"needYield": NumberInt("0"),
"saveState": NumberInt("65"),
"restoreState": NumberInt("65"),
"isEOF": NumberInt("1"),
"docsExamined": NumberInt("8321"),
"alreadyHasObj": NumberInt("0"),
"inputStage": {
// IXSCAN使用索引执行查询,如果是COLLSCAN表示集合扫描进行查询
"stage": "IXSCAN",
"nReturned": NumberInt("8321"),
"executionTimeMillisEstimate": NumberInt("0"),
"works": NumberInt("8322"),
"advanced": NumberInt("8321"),
"needTime": NumberInt("0"),
// 为了让写请求顺利执行,本次查询让步(暂停)的次数
"needYield": NumberInt("0"),
"saveState": NumberInt("65"),
"restoreState": NumberInt("65"),
"isEOF": NumberInt("1"),
"keyPattern": {
"age": 1,
"username": 1
},
"indexName": "age_1_username_1",
"isMultiKey": false,
"multiKeyPaths": {
"age": [ ],
"username": [ ]
},
"isUnique": false,
"isSparse": false,
"isPartial": false,
"indexVersion": NumberInt("2"),
"direction": "forward",
// 索引是如何被使用的,给出索引遍历范围
"indexBounds": {
"age": [
"[42.0, 42.0]"
],
"username": [
"[MinKey, MaxKey]"
]
},
"keysExamined": NumberInt("8321"),
"seeks": NumberInt("1"),
"dupsTested": NumberInt("0"),
"dupsDropped": NumberInt("0")
}
}
},
"serverInfo": {
"host": "4a8812679047",
"port": NumberInt("27017"),
"version": "4.2.6",
"gitVersion": "20364840b8f1af16917e4c23c1b5f5efd8b352f8"
},
"ok": 1
}
4. 何时不使用索引

索引在提交较小子数据集时最高效,当结果集在原集合所占百分比大, 则低效,因为使用索引需要两个查询:一次是查询索引项,在根据索引指针查询指向的文档,而全表查询只需要一次查询:查找文档

5. 索引类型
5.1 唯一索引

唯一索引确保每个值在索引中只会出现一次。如果保证不同文档的'firstname'键拥有不通的值,则可如下

db.getCollection('users').createIndex({'firstname': 1}, {'unique': true, 'partialFilterExpression': {'firstname': {$exists: true}}})

当重复键出现时会出现

db.getCollection('users').insert({'firstname': 'shen'})
> [Error] index 0: 11000 - E11000 duplicate key error collection: study.users index: firstname_1 dup key: { firstname: \"shen\" }
> 时间: 0.022s
5.2 部分索引

部分索引不是唯一的,要创建部分索引,将唯一索引{unique: true}去掉即可

欢迎关注公众号算法小生沈健的技术博客

5.MongoDB系列之索引(二)的更多相关文章

  1. mongoDB系列之(二):mongoDB 副本集

    1. 什么是副本集 副本集就是mongoDB副本所组成的一个集群. 同期原理是,写操作发生在主库,从库同步主库的OpLog日志. 集群中没有特定的主库,主库是选举产生,如果主库down了,会再选举出一 ...

  2. MongoDB系列一(索引及C#如何操作MongoDB)

    索引总概况 db.test.ensureIndex({"username":1})//创建索引 db.test.ensureIndex({"username": ...

  3. 4.MongoDB系列之索引(一)

    1. 执行计划查看 db.getCollection('users').find({'username': 'shenjian'}).explain('executionStats') 结果查看,先大 ...

  4. CRL快速开发框架系列教程十二(MongoDB支持)

    本系列目录 CRL快速开发框架系列教程一(Code First数据表不需再关心) CRL快速开发框架系列教程二(基于Lambda表达式查询) CRL快速开发框架系列教程三(更新数据) CRL快速开发框 ...

  5. MongoDB系列(二):C#应用

    前言 上一篇文章<MongoDB系列(一):简介及安装>已经介绍了MongoDB以及其在window环境下的安装,这篇文章主要讲讲如何用C#来与MongoDB进行通讯.再次强调一下,我使用 ...

  6. MongoDB系列之二(主动复制)

    目前我正在进行MongoDB的双机热备方面相关的工作.根据我目前看到的MongoDB方面的材料,MongoDB的实际部署有三种方式,分别是“主动复制”,“副本集”以及“分片副本集”. 首先我们从最简单 ...

  7. MongoDB开发深入之二:索引

    索引分类: 默认索引 单一索引 复合索引 多键索引(数组索引) 全文检索索引 2dsphere 索引 2D索引 ...... 索引属性: 到期TTL 唯一索引 部分索引 稀疏索引 索引通常能够极大的提 ...

  8. Node.js学习系列总索引

    Node.js学习系列也积累了一些了,建个总索引方便相互交流学习,后面会持续更新^_^! 尽量写些和实战相关的,不讲太多大道理... Node.js学习笔记系列总索引 Nodejs学习笔记(一)--- ...

  9. MongoDB学习笔记(索引)

    一.索引基础:    MongoDB的索引几乎与传统的关系型数据库一模一样,这其中也包括一些基本的优化技巧.下面是创建索引的命令:    > db.test.ensureIndex({" ...

随机推荐

  1. async...await在tcp通讯中的正确用法

    引言 编程能力在不断的总结中进步以及成长,最近的半年里,对之前的开源项目代码进行回归,在重构的过程中进行了很多思考,很多次都想放弃重构,毕竟一个已经在使用的项目,重构基础代码就相当于重新开发了,不过最 ...

  2. Linux 11 安装Tomcat

    参考源 https://www.bilibili.com/video/BV187411y7hF?spm_id_from=333.999.0.0 版本 本文章基于 CentOS 7.6 这里使用解压缩方 ...

  3. 我就获取个时间,机器就down了

    本文主要讲解linux 时间管理系统中的一个问题 背景:linux 时间管理,包含clocksource,clockevent,timer,tick,timekeeper等等概念 , 这些概念有机地组 ...

  4. [CF1519C] Berland Regional (数论分块)

    题面 有 n 个学生和 n 所大学,每个学生在其中一所大学中学习,且各有一个能力值 s i s_i si​ . 某次组队打比赛的召集令会给一个数字 k ,表示团队数量.然后每所大学会先把自己的所有学生 ...

  5. 【java】IDEA-jar包导出与导入

    导出步骤: 1.CTRL + SHIFT + ALT + S 2.选择:Artifacts ,点击"+",在添加页面中选择:JAR-From modules with depend ...

  6. Mysql数据库安装到操作到应用

    该博文转载(https://www.cnblogs.com/whwh/p/16200066.html) 一.安装和配置数据库: 下载mysql地址:https://dev.mysql.com/down ...

  7. Linux有趣命令

    通外网 下载使用阿里云镜像源:wget -O /etc/yum.repos.d/CentOS-Base.repo https://mirrors.aliyun.com/repo/Centos-7.re ...

  8. KingbaseES R3 集群pcp_attach_node 更新show pool_nodes中节点状态

    系统环境: 操作系统: [kingbase@node2 bin]$ cat /etc/centos-release CentOS Linux release 7.2.1511 (Core) 数据库: ...

  9. docker-compose概述--翻译

    Overview of Docker Compose 译文 Docker Compose 是一个用来定义和执行多Docker容器程序的工具,如果使用Compose,你将可以使用一个YAML文件来配置你 ...

  10. EntityFrameworkCore 模型自动更新(下)

    话题 上一篇我们讨论到获取将要执行的迁移操作,到这一步为止,针对所有数据库都通用,在此之后需要生成SQL脚本对于不同数据库将有不同差异,我们一起来瞅一瞅 SQLite脚本生成差异 在上一篇拿到的迁移操 ...