MongoDB支持的索引类型


Posted in MongoDB onApril 11, 2022

MongoDB 4.2官方支持索引类型如下:

  • 单字段索引
  • 复合索引
  • 多键索引
  • 文本索引
  • 2dsphere索引
  • 2d索引
  • geoHaystack索引
  • 哈希索引

单字段索引

在单个字段上创建升序索引

handong1:PRIMARY> db.test.getIndexes()
[
	{
		"v" : 2,
		"key" : {
			"_id" : 1
		},
		"name" : "_id_",
		"ns" : "db6.test"
	}
]

在字段id上添加升序索引

handong1:PRIMARY> db.test.createIndex({"id":1})
{
	"createdCollectionAutomatically" : false,
	"numIndexesBefore" : 1,
	"numIndexesAfter" : 2,
	"ok" : 1,
	"$clusterTime" : {
		"clusterTime" : Timestamp(1621322378, 1),
		"signature" : {
			"hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="),
			"keyId" : NumberLong(0)
		}
	},
	"operationTime" : Timestamp(1621322378, 1)
}
handong1:PRIMARY> db.test.getIndexes()
[
	{
		"v" : 2,
		"key" : {
			"_id" : 1
		},
		"name" : "_id_",
		"ns" : "db6.test"
	},
	{
		"v" : 2,
		"key" : {
			"id" : 1
		},
		"name" : "id_1",
		"ns" : "db6.test"
	}
]
handong1:PRIMARY> db.test.find({"id":100})
{ "_id" : ObjectId("60a35d061f183b1d8f092114"), "id" : 100, "name" : "handong", "ziliao" : { "name" : "handong", "age" : 25, "hobby" : "mongodb" } }

上述查询可以使用新建的单字段索引。

在嵌入式字段上创建索引

handong1:PRIMARY> db.test.createIndex({"ziliao.name":1})
{
	"createdCollectionAutomatically" : false,
	"numIndexesBefore" : 2,
	"numIndexesAfter" : 3,
	"ok" : 1,
	"$clusterTime" : {
		"clusterTime" : Timestamp(1621323677, 2),
		"signature" : {
			"hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="),
			"keyId" : NumberLong(0)
		}
	},
	"operationTime" : Timestamp(1621323677, 2)
}

以下查询可以用的新建的索引。

db.test.find({"ziliao.name":"handong"})

在内嵌文档上创建索引

handong1:PRIMARY> db.test.createIndex({ziliao:1})
{
	"createdCollectionAutomatically" : false,
	"numIndexesBefore" : 3,
	"numIndexesAfter" : 4,
	"ok" : 1,
	"$clusterTime" : {
		"clusterTime" : Timestamp(1621324059, 2),
		"signature" : {
			"hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="),
			"keyId" : NumberLong(0)
		}
	},
	"operationTime" : Timestamp(1621324059, 2)
}

以下查询可以使用新建的索引。

db.test.find({ziliao:{ "name" : "handong", "age" : 25, "hobby" : "mongodb" }})

复合索引

创建复合索引

db.user.createIndex({"product_id":1,"type":-1})

以下查询可以用到新建的复合索引

db.user.find({"product_id":"e5a35cfc70364d2092b8f5d14b1a3217","type":0})

多键索引

基于一个数组创建索引,MongoDB会自动创建为多键索引,无需刻意指定。
多键索引也可以基于内嵌文档来创建。
多键索引的边界值的计算依赖于特定的规则。
查看文档:

handong1:PRIMARY> db.score.find()
{ "_id" : ObjectId("60a32d7f1f183b1d8f0920ad"), "name" : "dandan", "age" : 30, "score" : [ { "english" : 90, "math" : 99, "physics" : 88 } ], "is_del" : false }
{ "_id" : ObjectId("60a32d8b1f183b1d8f0920ae"), "name" : "dandan", "age" : 30, "score" : [ 99, 98, 97, 96 ], "is_del" : false }
{ "_id" : ObjectId("60a32d9a1f183b1d8f0920af"), "name" : "dandan", "age" : 30, "score" : [ 100, 100, 100, 100 ], "is_del" : false }
{ "_id" : ObjectId("60a32e8c1f183b1d8f0920b0"), "name" : "dandan", "age" : 30, "score" : [ { "english" : 70, "math" : 99, "physics" : 88 } ], "is_del" : false }
{ "_id" : ObjectId("60a37b141f183b1d8f0aa751"), "name" : "dandan", "age" : 30, "score" : [ 96, 95 ] }
{ "_id" : ObjectId("60a37b1d1f183b1d8f0aa752"), "name" : "dandan", "age" : 30, "score" : [ 96, 95, 94 ] }
{ "_id" : ObjectId("60a37b221f183b1d8f0aa753"), "name" : "dandan", "age" : 30, "score" : [ 96, 95, 94, 93 ] }

创建score字段多键索引:

db.score.createIndex("score":1)
handong1:PRIMARY> db.score.find({"score":[ 96, 95 ]})
{ "_id" : ObjectId("60a37b141f183b1d8f0aa751"), "name" : "dandan", "age" : 30, "score" : [ 96, 95 ] }

查看执行计划:

handong1:PRIMARY> db.score.find({"score":[ 96, 95 ]}).explain()
{
	"queryPlanner" : {
		"plannerVersion" : 1,
		"namespace" : "db6.score",
		"indexFilterSet" : false,
		"parsedQuery" : {
			"score" : {
				"$eq" : [
					96,
					95
				]
			}
		},
		"queryHash" : "8D76FC59",
		"planCacheKey" : "E2B03CA1",
		"winningPlan" : {
			"stage" : "FETCH",
			"filter" : {
				"score" : {
					"$eq" : [
						96,
						95
					]
				}
			},
			"inputStage" : {
				"stage" : "IXSCAN",
				"keyPattern" : {
					"score" : 1
				},
				"indexName" : "score_1",
				"isMultiKey" : true,
				"multiKeyPaths" : {
					"score" : [
						"score"
					]
				},
				"isUnique" : false,
				"isSparse" : false,
				"isPartial" : false,
				"indexVersion" : 2,
				"direction" : "forward",
				"indexBounds" : {
					"score" : [
						"[96.0, 96.0]",
						"[[ 96.0, 95.0 ], [ 96.0, 95.0 ]]"
					]
				}
			}
		},
		"rejectedPlans" : [ ]
	},
	"serverInfo" : {
		"host" : "mongo3",
		"port" : 27017,
		"version" : "4.2.12",
		"gitVersion" : "5593fd8e33b60c75802edab304e23998fa0ce8a5"
	},
	"ok" : 1,
	"$clusterTime" : {
		"clusterTime" : Timestamp(1621326912, 1),
		"signature" : {
			"hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="),
			"keyId" : NumberLong(0)
		}
	},
	"operationTime" : Timestamp(1621326912, 1)
}

可以看到已经使用了新建的多键索引。

文本索引

    为了支持对字符串内容的文本搜索查询,MongoDB提供了文本索引。文本(text )索引可以包含任何值为字符串或字符串元素数组的字段

db.user.createIndex({"sku_attributes":"text"})
db.user.find({$text:{$search:"测试"}})

查看执行计划:

handong1:PRIMARY> db.user.find({$text:{$search:"测试"}}).explain()
{
	"queryPlanner" : {
		"plannerVersion" : 1,
		"namespace" : "db6.user",
		"indexFilterSet" : false,
		"parsedQuery" : {
			"$text" : {
				"$search" : "测试",
				"$language" : "english",
				"$caseSensitive" : false,
				"$diacriticSensitive" : false
			}
		},
		"queryHash" : "83098EE1",
		"planCacheKey" : "7E2D582B",
		"winningPlan" : {
			"stage" : "TEXT",
			"indexPrefix" : {
				
			},
			"indexName" : "sku_attributes_text",
			"parsedTextQuery" : {
				"terms" : [
					"测试"
				],
				"negatedTerms" : [ ],
				"phrases" : [ ],
				"negatedPhrases" : [ ]
			},
			"textIndexVersion" : 3,
			"inputStage" : {
				"stage" : "TEXT_MATCH",
				"inputStage" : {
					"stage" : "FETCH",
					"inputStage" : {
						"stage" : "OR",
						"inputStage" : {
							"stage" : "IXSCAN",
							"keyPattern" : {
								"_fts" : "text",
								"_ftsx" : 1
							},
							"indexName" : "sku_attributes_text",
							"isMultiKey" : true,
							"isUnique" : false,
							"isSparse" : false,
							"isPartial" : false,
							"indexVersion" : 2,
							"direction" : "backward",
							"indexBounds" : {
								
							}
						}
					}
				}
			}
		},
		"rejectedPlans" : [ ]
	},
	"serverInfo" : {
		"host" : "mongo3",
		"port" : 27017,
		"version" : "4.2.12",
		"gitVersion" : "5593fd8e33b60c75802edab304e23998fa0ce8a5"
	},
	"ok" : 1,
	"$clusterTime" : {
		"clusterTime" : Timestamp(1621328543, 1),
		"signature" : {
			"hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="),
			"keyId" : NumberLong(0)
		}
	},
	"operationTime" : Timestamp(1621328543, 1)
}

可以看到通过文本索引可以查到包含测试关键字的数据。
**注意:**可以根据自己需要创建复合文本索引。

2dsphere索引

创建测试数据

db.places.insert(
   {
      loc : { type: "Point", coordinates: [ 116.291226, 39.981198 ] },
      name: "火器营桥",
      category : "火器营桥"
   }
)


db.places.insert(
   {
      loc : { type: "Point", coordinates: [ 116.281452, 39.914226 ] },
      name: "五棵松",
      category : "五棵松"
   }
)

db.places.insert(
   {
      loc : { type: "Point", coordinates: [ 116.378038, 39.851467 ] },
      name: "角门西",
      category : "角门西"
   }
)


db.places.insert(
   {
      loc : { type: "Point", coordinates: [ 116.467833, 39.881581 ] },
      name: "潘家园",
      category : "潘家园"
   }
)

db.places.insert(
   {
      loc : { type: "Point", coordinates: [ 116.468264, 39.914766 ] },
      name: "国贸",
      category : "国贸"
   }
)

db.places.insert(
   {
      loc : { type: "Point", coordinates: [ 116.46618, 39.960213 ] },
      name: "三元桥",
      category : "三元桥"
   }
)

db.places.insert(
   {
      loc : { type: "Point", coordinates: [ 116.400064, 40.007827 ] },
      name: "奥林匹克森林公园",
      category : "奥林匹克森林公园"
   }
)

添加2dsphere索引

db.places.createIndex( { loc : "2dsphere" } )
db.places.createIndex( { loc : "2dsphere" , category : -1, name: 1 } )

利用2dsphere索引查询多边形里的点

凤凰岭
[116.098234,40.110569]
天安门
[116.405239,39.913839]
四惠桥
[116.494351,39.912068]
望京
[116.494494,40.004594]

handong1:PRIMARY> db.places.find( { loc :
...                   { $geoWithin :
...                     { $geometry :
...                       { type : "Polygon" ,
...                         coordinates : [ [
...                                           [116.098234,40.110569] ,
...                                           [116.405239,39.913839] ,
...                                           [116.494351,39.912068] ,
...                                           [116.494494,40.004594] ,
...                                           [116.098234,40.110569]
...                                         ] ]
...                 } } } } )
{ "_id" : ObjectId("60a4c950d4211a77d22bf7f8"), "loc" : { "type" : "Point", "coordinates" : [ 116.400064, 40.007827 ] }, "name" : "奥林匹克森林公园", "category" : "奥林匹克森林公园" }
{ "_id" : ObjectId("60a4c94fd4211a77d22bf7f7"), "loc" : { "type" : "Point", "coordinates" : [ 116.46618, 39.960213 ] }, "name" : "三元桥", "category" : "三元桥" }
{ "_id" : ObjectId("60a4c94fd4211a77d22bf7f6"), "loc" : { "type" : "Point", "coordinates" : [ 116.468264, 39.914766 ] }, "name" : "国贸", "category" : "国贸" }

可以看到把集合中包含在指定四边形里的点,全部列了出来。

利用2dsphere索引查询球体上定义的圆内的点

handong1:PRIMARY> db.places.find( { loc :
...                   { $geoWithin :
...                     { $centerSphere :
...                        [ [ 116.439518, 39.954751 ] , 2/3963.2 ]
...                 } } } )
{ "_id" : ObjectId("60a4c94fd4211a77d22bf7f7"), "loc" : { "type" : "Point", "coordinates" : [ 116.46618, 39.960213 ] }, "name" : "三元桥", "category" : "三元桥" }

返回所有半径为经度 116.439518 E 和纬度 39.954751 N 的2英里内坐标。示例将2英里的距离转换为弧度,通过除以地球近似的赤道半径3963.2英里。

2d索引

在以下情况下使用2d索引:

  • 您的数据库具有来自MongoDB 2.2或更早版本的旧版旧版坐标对。
  • 您不打算将任何位置数据存储为GeoJSON对象。

哈希索引

要创建hashed索引,请指定 hashed 作为索引键的值,如下例所示:

handong1:PRIMARY> db.test.createIndex({"_id":"hashed"})
{
	"createdCollectionAutomatically" : false,
	"numIndexesBefore" : 4,
	"numIndexesAfter" : 5,
	"ok" : 1,
	"$clusterTime" : {
		"clusterTime" : Timestamp(1621419338, 1),
		"signature" : {
			"hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="),
			"keyId" : NumberLong(0)
		}
	},
	"operationTime" : Timestamp(1621419338, 1)
}

注意事项

  • MongoDB支持任何单个字段的 hashed 索引。hashing函数折叠嵌入的文档并计算整个值的hash值,但不支持多键(即.数组)索引。
  • 您不能创建具有hashed索引字段的复合索引,也不能在索引上指定唯一约束hashed;但是,您可以hashed在同一字段上创建索引和升序/降序(即非哈希)索引:MongoDB将对范围查询使用标量索引。

 到此这篇关于MongoDB索引类型汇总分享的文章就介绍到这了,更多相关MongoDB索引内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

MongoDB 相关文章推荐
MongoDB使用profile分析慢查询的步骤
Apr 30 MongoDB
MongoDB数据库的安装步骤
Jun 18 MongoDB
MongoDB 常用的crud操作语句
Jun 20 MongoDB
MongoDB orm框架的注意事项及简单使用
Jun 20 MongoDB
详解MongoDB的条件查询和排序
Jun 23 MongoDB
Mongo服务重启异常问题的处理方法
Jul 01 MongoDB
Centos系统通过Docker安装并搭建MongoDB数据库
Apr 12 MongoDB
MongoDB数据库之添删改查
Apr 26 MongoDB
NoSQL优缺点与MongoDB数据库简介
Jun 05 MongoDB
MongoDB支持的数据类型
Apr 11 #MongoDB
MongoDB误操作后使用oplog恢复数据
Apr 11 #MongoDB
mongoDB数据库索引快速入门指南
MongoDB数据库部署环境准备及使用介绍
一次线上mongo慢查询问题排查处理记录
Mar 18 #MongoDB
SpringBoot 整合mongoDB并自定义连接池的示例代码
Feb 28 #MongoDB
剖析后OpLog订阅MongoDB的数据变更就没那么难了
You might like
删除无限级目录与文件代码共享
2006/07/12 PHP
PHP中用接口、抽象类、普通基类实现“面向接口编程”与“耦合方法”简述
2011/03/23 PHP
Laravel5中contracts详解
2015/03/02 PHP
微信公众平台实现获取用户OpenID的方法
2015/04/15 PHP
php单一接口的实现方法
2015/06/20 PHP
Mac系统完美安装PHP7详细教程
2017/06/06 PHP
PHP使用glob方法遍历文件夹下所有文件的实例
2018/10/17 PHP
[原创]静态页面也可以实现预览 列表不同的显示方式
2006/10/14 Javascript
自制的文件上传JS控件可支持IE、chrome、firefox etc
2014/04/18 Javascript
提升PHP安全:8个必须修改的PHP默认配置
2014/11/17 Javascript
在JavaScript中操作时间之getUTCDate()方法的使用
2015/06/10 Javascript
JavaScript中的Function函数
2015/08/27 Javascript
弹出遮罩层后禁止滚动效果【实现代码】
2016/04/29 Javascript
js控制台输出的方法(详解)
2016/11/26 Javascript
Node.js从字符串生成文件流的实现方法
2019/08/18 Javascript
解决layui数据表格排序图标被超出的表头挤出去的问题
2019/09/19 Javascript
JavaScript实现文件下载并重命名代码实例
2019/12/12 Javascript
原生js生成图片验证码
2020/10/11 Javascript
python进程管理工具supervisor使用实例
2014/09/17 Python
python爬虫之BeautifulSoup 使用select方法详解
2017/10/23 Python
Django Channels 实现点对点实时聊天和消息推送功能
2019/07/17 Python
CSS3 icon font完全指南(CSS3 font 会取代icon图标)
2013/01/06 HTML / CSS
CSS3实现文字波浪线效果示例代码
2016/11/20 HTML / CSS
Clearly澳大利亚:购买眼镜、太阳镜和隐形眼镜
2018/04/26 全球购物
仓库组长岗位职责
2014/01/29 职场文书
幼儿园教学随笔感言
2014/02/23 职场文书
演讲主持词
2014/03/18 职场文书
初婚初育证明范本
2014/11/24 职场文书
健康状况证明书
2014/11/26 职场文书
英语教师个人工作总结
2015/02/09 职场文书
小班上学期个人总结
2015/02/12 职场文书
本科毕业论文致谢词
2015/05/14 职场文书
2015年学校团委工作总结
2015/05/26 职场文书
新闻稿件写作范文
2015/07/18 职场文书
2015年教导处教学工作总结
2015/07/22 职场文书
2016党员学习作风建设心得体会
2016/01/21 职场文书