获取数组内唯一字段值的聚合查询:索引与查询优化咨询
MongoDB聚合查询优化方案
一、索引优化建议
基础索引:创建
status字段的单字段索引,加速初始过滤阶段:db.yourCollection.createIndex({ status: 1 })这个索引能帮MongoDB快速过滤掉
status为ARCHIVED的文档,减少后续聚合阶段需要处理的数据量。虽然$ne的索引效率不如$eq,但比全表扫描提升明显。进阶覆盖索引:如果数据量较大,建议创建复合覆盖索引,让查询完全从索引获取数据,无需回表读取完整文档:
db.yourCollection.createIndex({ status: 1, "dataRecords.dataSets.name": 1 })这个索引既满足
$match的过滤需求,又能直接提供dataRecords.dataSets.name字段的值,大幅降低IO开销。
二、查询语句简化优化
原查询的分组和解包步骤存在冗余,可简化为以下逻辑,减少中间数据处理:
aggregate([ { "$match": { "status": { "$ne": "ARCHIVED" }}}, { "$unwind": "$dataRecords.dataSets" }, // 直接解包原数组 { "$group": { "_id": "$dataRecords.dataSets.name" }}, // 直接按name去重 { "$sort": { "_id": 1 }}, { "$skip": 0 }, { "$limit": 20 } ])
优化逻辑说明:
- 原查询先按每个文档的
name数组分组,再解包后重新分组去重,属于重复操作。直接解包原dataSets数组后按name分组,一步完成去重,减少了一次分组和解包的计算开销。
内容的提问来源于stack exchange,提问作者zibi
相关产品推荐
相关产品推荐

