大数据量使用全集合查询,这是非常影响性能的,而索引可以加快查询效率,提高性能,所以这方面的知识也是必不可少的。
查询分析
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()
里面有可以选择不同的参数queryPlanner
、executionStats
和allPlansExecution
,默认是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()