MongoDB之索引

大数据量使用全集合查询,这是非常影响性能的,而索引可以加快查询效率,提高性能,所以这方面的知识也是必不可少的。

查询分析

explain()可以帮助我们分析查询语句性能。

语法

复制代码
db.collection.find(...).explain()

案例及结果

案例
复制代码
db.person.find({name:"plf"}).explain()
结果
复制代码
{
"queryPlanner" : {
	"plannerVersion" : 1,
	"namespace" : "test.person",
	"indexFilterSet" : false,
	"parsedQuery" : {
	        "name" : {
	                "$eq" : "plf"
	        }
	},
	"winningPlan" : {
        "stage" : "FETCH",
        "inputStage" : {
            "stage" : "IXSCAN",
            "keyPattern" : {
                    "name" : 1
            },
            "indexName" : "name_1",
            "isMultiKey" : false,
            "multiKeyPaths" : {
                    "name" : [ ]
            },
            "isUnique" : false,
            "isSparse" : false,
            "isPartial" : false,
            "indexVersion" : 2,
            "direction" : "forward",
            "indexBounds" : {
                    "name" : [
                            "[\"plf\", \"plf\"]"
                    ]
            }
        }
	},
	"rejectedPlans" : [ ]
},
"executionStats" : {
    "executionSuccess" : true,
    "nReturned" : 1,
    "executionTimeMillis" : 0,
    "totalKeysExamined" : 1,
    "totalDocsExamined" : 1,
    "executionStages" : {
        "stage" : "FETCH",
        "nReturned" : 1,
        "executionTimeMillisEstimate" : 0,
        "works" : 2,
        "advanced" : 1,
        "needTime" : 0,
        "needYield" : 0,
        "saveState" : 0,
        "restoreState" : 0,
        "isEOF" : 1,
        "invalidates" : 0,
        "docsExamined" : 1,
        "alreadyHasObj" : 0,
        "inputStage" : {
            "stage" : "IXSCAN",
            "nReturned" : 1,
            "executionTimeMillisEstimate" : 0,
            "works" : 2,
            "advanced" : 1,
            "needTime" : 0,
            "needYield" : 0,
            "saveState" : 0,
            "restoreState" : 0,
            "isEOF" : 1,
            "invalidates" : 0,
            "keyPattern" : {
                    "name" : 1
            },
            "indexName" : "name_1",
            "isMultiKey" : false,
            "multiKeyPaths" : {
                    "name" : [ ]
            },
            "isUnique" : false,
            "isSparse" : false,
            "isPartial" : false,
            "indexVersion" : 2,
            "direction" : "forward",
            "indexBounds" : {
                    "name" : [
                            "[\"plf\", \"plf\"]"
                    ]
            },
            "keysExamined" : 1,
            "seeks" : 1,
            "dupsTested" : 0,
            "dupsDropped" : 0,
            "seenInvalidated" : 0
    }
}
},
"serverInfo" : {
    "host" : ".",
    "port" : 27017,
    "version" : "3.5.11-226-g5831278",
    "gitVersion" : "."
},
"ok" : 1
}
结果注释
复制代码
namespace:该值返回的是该query所查询的表
indexfilter:是否使用了索引过滤(index filter)
winningPlan:查询优化器针对该query所返回的最优执行计划的详细内容
winningPlan.stage:最优执行计划的stage
winningPlan.inputStage:explain.queryPlanner.winningPlan.stage的child stage
winningPlan.inputStage.keyPattern:所扫描的index内容,此处是w:1与n:1
winningPlan.inputStage.indexName:winning plan所选用的index
winningPlan.inputStage.isMultiKey:是否是Multikey,此处返回是false,如果索引建立在array上,此处将是true
winningPlan.inputStage.direction:此query的查询顺序,此处是forward,如果用了.sort({w:-1})将显示backward
winningPlan.inputStage.indexBounds:winningplan所扫描的索引范围。
rejectedPlans:其他执行计划(非最优而被查询优化器reject的)的详细返回


executionSuccess:是否执行成功
nReturned:查询的返回条数
executionTimeMillis:整体执行时间
totalKeysExamined:扫描索引条目的数量
totalDocsExamined:扫描文档的数量
executionStages.nReturned:意义与nReturned一样
executionStages.executionTimeMillisEstimate:意义与executionTimeMillis一样
executionStages.docsExamined:意义与totalDocsExamined一样
executionStages.executionStats.inputStage中:的与上述理解方式相同

stage分类

复制代码
COLLSCAN:扫描整个集合 
IXSCAN:索引扫描 
FETCH:根据索引去检索选择document
SHARD_MERGE:将各个分片返回数据进行merge
SORT:表明在内存中进行了排序(与老版本的scanAndOrder:true一致)
LIMIT:使用limit限制返回数
SKIP:使用skip进行跳过 IDHACK:针对_id进行查
SHARDING_FILTER:通过mongos对分片数据进行查询
COUNT:利用db.coll.explain().count()之类进行count
COUNTSCAN:count不使用用Index进行count时的stage返回
COUNT_SCAN:count使用了Index进行count时的stage返回 SUBPLA:未使用到索引的$or查询的stage返回
TEXT:使用全文索引进行查询时候的stage返回 PROJECTION:限定返回字段时候stage的返回
注意点

目前使用MongoDB版本为3.5所以explain()有所不同

  • 1、explain()里面有可以选择不同的参数queryPlannerexecutionStatsallPlansExecution,默认是queryPlanner,不同的参数返回值都不同.
  • 2、explain()返回很多参数可以参考官方文档
  • 3、queryPlanner模式下并不会去真正进行query语句查询,而是针对query语句进行执行计划分析并选出winning plan

索引语法

创建索引

复制代码
db.collection.createIndex(keys, options)

目前3.0版本以上建议使用db.collection.createIndex()代替db.collection.ensureIndex(keys, options)

其中keys官方说明:包含字段和值对的文档,其中字段是索引键,值描述该字段的索引类型。对于字段上的升序索引,请指定一个值1; 为了降序索引,指定一个值-1。

options的可选值

参数 类型 描述
background 布尔 可选的。在后台构建索引所以操作不会阻止其他数据库操作。指定true在后台构建。默认值是false。
unique 布尔 可选的。创建唯一索引,以便集合不接受索引键值与索引中现有值匹配的文档的插入或更新。
name 字符串 可选的。索引的名称。如果未指定,MongoDB通过连接索引字段的名称和排序顺序来生成索引名称。
partialFilterExpression 文件 可选的。如果指定,则索引仅引用与过滤器表达式匹配的文档。
sparse 布尔 可选的。如果true该索引仅引用具有指定字段的文档
expireAfterSeconds 整数 可选的。指定一个值(以秒为单位)作为TTL来控制MongoDB保留此集合中文档的时间。
storageEngine 文件 可选的。允许用户在创建索引时按每个索引配置存储引擎
collation 文件 可选的。指定索引的排序规则。

collation详情

复制代码
collation: {
   locale: <string>,
   caseLevel: <boolean>,
   caseFirst: <string>,
   strength: <int>,
   numericOrdering: <boolean>,
   alternate: <string>,
   maxVariable: <string>,
   backwards: <boolean>
}
指定排序规则时,该locale字段是强制性的; 所有其他整理字段都是可选的。

复制代码
db.collection.createIndexes([keyPattern,],options)

3.2版本中的新功能,在集合上创建一个或多个索引。

删除索引

复制代码
db.collection.dropIndex(index)

复制代码
db.collection.dropIndexes()

上述命令是删除_id字段以外的所有索引

MongoDB里面没有修改索引,只能先删除索引再创建索引。

查询索引

复制代码
db.collection.getIndexes()
相关推荐
q***816444 分钟前
MySQL:数据查询-limit
数据库·mysql
p***924844 分钟前
DBeaver连接本地MySQL、创建数据库表的基础操作
数据库·mysql
JIngJaneIL2 小时前
社区互助|社区交易|基于springboot+vue的社区互助交易系统(源码+数据库+文档)
java·数据库·vue.js·spring boot·论文·毕设·社区互助
晚风吹人醒.2 小时前
缓存中间件Redis安装及功能演示、企业案例
linux·数据库·redis·ubuntu·缓存·中间件
Y***98513 小时前
DVWA靶场通关——SQL Injection篇
数据库·sql
Yawesh_best3 小时前
告别系统壁垒!WSL+cpolar 让跨平台开发效率翻倍
运维·服务器·数据库·笔记·web安全
蒋士峰DBA修行之路3 小时前
实验二十八 SQL PATCH调优
数据库·sql·gaussdb
I***t7163 小时前
一条sql 在MySQL中是如何执行的
数据库·sql·mysql
一 乐3 小时前
应急知识学习|基于springboot+vue的应急知识学习系统(源码+数据库+文档)
数据库·vue.js·spring boot
微学AI4 小时前
内网穿透的应用-突破局域网束缚,MongoDB 远程访问使用cpolar原来可以这么简单
数据库·mongodb