如何通过MongoDB聚合查询实现学生按成绩分组的列表
MongoDB按字母成绩分组并收集学生姓名的聚合查询
直接通过$group结合$addToSet就能实现需求,无需手动指定成绩值,完整查询结构如下:
db.Students.aggregate([ { $group: { _id: "$grades", student_names: { $addToSet: "$student_name" } } }, { $project: { _id: 0, grade: "$_id", student_names: 1 } } ])
各阶段作用说明:
- $group阶段:
- 以
grades字段作为分组依据(_id: "$grades"),MongoDB会自动识别集合中所有不同的字母成绩并完成分组,无需手动枚举。 $addToSet: "$student_name"会把每组内的学生姓名去重后收集为数组,如果不需要去重(允许同姓名学生存在),可以替换为$push。
- 以
- $project阶段:
- 调整输出格式,将原分组依据的
_id重命名为grade,同时隐藏原_id字段,让结果更贴近你需要的直观结构。
- 调整输出格式,将原分组依据的
输出示例:
[ { "grade": "A+", "student_names": ["Chris", "Ada", "Lee"] }, { "grade": "A", "student_names": ["Tom", "Jerry"] }, { "grade": "B", "student_names": ["Lucy"] } ]
如果希望输出直接是成绩为键、姓名数组为值的对象结构,可以追加$arrayToObject和$replaceRoot阶段:
db.Students.aggregate([ { $group: { _id: "$grades", student_names: { $addToSet: "$student_name" } } }, { $project: { data: { k: "$_id", v: "$student_names" } } }, { $group: { _id: null, result: { $push: "$data" } } }, { $replaceRoot: { newRoot: { $arrayToObject: "$result" } } } ])
该方式的输出示例:
{ "A+": ["Chris", "Ada", "Lee"], "A": ["Tom", "Jerry"], "B": ["Lucy"] }
内容的提问来源于stack exchange,提问作者Owen S
相关产品推荐
相关产品推荐

