MongoDB的索引是数据库性能优化的关键因素,与MySQL、Oracle等关系型数据库中的索引原理相似,但具有自身的特性和限制。MongoDB的索引建立在Collection(表)级别,采用B-树数据结构来加速查询和排序操作。
1. 默认索引:MongoDB会在每个Collection上自动创建一个唯一的 `_id` 索引,用于标识每条文档的唯一性。如果未明确指定,MongoDB将自动生成该索引并为其分配值。
2. 单域索引:允许针对集合中的单个字段创建索引,例如 `db.records.ensureIndex( { userid: 1 } )`,这将加速对`userid`字段的查询。
3. 复合域索引:可以同时为多个字段创建索引,例如 `db.collection.ensureIndex( { a: 1, b: 1, c: 1 } )`,顺序很重要,影响查询优化。这种索引支持多个查询条件的组合。
4. 复合键索引:特别适用于数组字段内的元素,可以对数组中的每个元素创建索引。
5. 地理索引:专为地理位置数据设计,支持地理空间查询,如查找附近位置等。
6. 文本索引:用于全文搜索,不存储停顿词和主干词,只存储基础词根,提高文本搜索效率。
7. 哈希索引:仅支持等值匹配查询,不支持范围查询,适合用于哈希函数的结果。
8. 唯一性索引:确保特定字段的值在集合中唯一,如 `db.accounts.ensureIndex( { "tax-id": 1 }, { unique: true } )`。
9. 稀疏索引:仅包含包含索引字段的文档,允许多个没有指定字段的文档存在,提高存储效率。
10. 索引交叉:复杂查询可能需要多个索引配合,是否使用复合索引还是多个单索引取决于具体查询和系统环境。
11. 策略创建索引:创建索引应根据查询需求,如创建单键索引支持单键查询,或创建复合索引支持多种查询和排序。
12. 覆盖查询:当索引包含所有查询所需的信息时,可以进行覆盖查询,减少对原始文档的访问。例如,`db.users.ensureIndex( { status: 1, user: 1 } )` 和 `db.users.find( { status: "A" }, { user: 1, _id: 0 } )`。需要注意的是,数组字段和嵌套文档的索引通常不能形成覆盖。
13. 使用`explain()`方法可以检查查询是否为覆盖查询,如果`indexOnly`为`true`,则表示查询是覆盖查询。
通过合理地设计和利用索引,MongoDB能够显著提升查询性能,尤其是对于大型数据集和复杂查询场景。了解和掌握MongoDB的索引特性,对于优化数据库性能至关重要。