聚合查询(分组、聚合、运算)
通过聚合查询,您可以进行数据处理、转换、筛选、统计、排序、分组、联接,支持复杂逻辑运算;注意聚合查询是一个相对复杂的概念。
使用 db.collection(<collection_name>)
对象中的 aggregate
方法,您可以进行聚合查询操作。
操作符
方法 | 描述 |
---|---|
$project | 重命名、增加或删除字段。 |
$match | 过滤数据,只返回符合条件的数据。 |
$group | 分组聚合操作,对数据进行分组并应用聚合函数。 |
$sort | 对数据进行排序。 |
$limit | 限制结果集中返回的数据数量。 |
$skip | 跳过指定数量的数据,返回剩余的数据。 |
$unwind | 展开数组,将数组字段拆分为多个数据,每个数据包含数组中的一个元素。 |
$group | 对分组的数据执行累加、求平均值等聚合操作。 |
$lookup | 执行左连接,从其他集合中获取匹配的数据。 |
$addFields | 增加新的字段到数据中。 |
$replaceRoot | 用指定的数据替换结果集中的数据。 |
$out | 将结果集写入新的集合。 |
$facet | 允许在同一次查询中执行多个独立的聚合操作,并返回多个结果集。 |
聚合函数
函数 | 描述 |
---|---|
$sum | 计算指定字段的总和。 |
$avg | 计算指定字段的平均值。 |
$min | 找出指定字段的最小值。 |
$max | 找出指定字段的最大值。 |
$push | 将指定字段的值添加到数组中。 |
$addToSet | 将指定字段的唯一值添加到集合中。 |
$first | 返回指定字段的第一个文档值。 |
$last | 返回指定字段的最后一个文档值。 |
$stdDevPop | 计算指定字段的总体标准差。 |
$stdDevSamp | 计算指定字段的样本标准差。 |
$meta | 在文本搜索中返回文档的元数据,例如文本匹配的分数。 |
$size | 返回数组字段的长度。 |
$slice | 从数组中返回指定范围的元素。 |
$filter | 根据条件过滤数组中的元素。 |
$regexMatch | 使用正则表达式匹配文本字段。 |
$expr | 允许在聚合管道中使用表达式。 |
$match 匹配
js
function main() {
let query = [
{
$match: {
name: '王华',
},
},
]
let result = db.collection('students').aggregate(query) // 查询 students 集合中 name 为 王华 的数据
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
js
function main() {
let query = [
{
$match: {
name: '王华',
age: 21,
},
},
]
let result = db.collection('students').aggregate(query) // 查询 students 集合中 name 为 王华 并且 age 为 21 的数据
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
js
function main() {
let query = [
{
$match: {
name: '王华',
age: { $lt: 18 },
},
},
]
let result = db.collection('students').aggregate(query) // 查询 students 集合中 name 为 王华 并且 age 小于 18 的数据
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
$project 重新定义结构
js
function main() {
let query = [
{
$project: { _id: 0, name: 1, age: 1 }, // 0 为排除、1 为包含
},
]
let result = db.collection('students').aggregate(query) // 只查询 students 集合中的 name 和 age 字段数据
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
js
function main() {
let query = [
{
$match: {
name: '王华',
age: { $lt: 18 },
},
},
{
$project: { _id: 0, name: 1, age: 1 }, // 0 为排除、1 为包含
},
]
let result = db.collection('students').aggregate(query) // 查询 students 集合中 name 为 王华 并且 age 小于 18 的 name 和 age 字段数据
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
$sum 计算总和
js
function main() {
let query = [
{
$group: {
_id: '$name',
count: {
$sum: 1,
},
},
},
]
let result = db.collection('students').aggregate(query) // 统计 students 集合中 name 相同的学生数量
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
js
function main() {
let query = [
{
$group: {
_id: null,
count: {
$sum: '$age',
},
},
},
]
let result = db.collection('students').aggregate(query) // 计算 students 集合中所有学生的年龄总和
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
$avg 计算平均值
js
function main() {
let query = [
{
$group: {
_id: null,
avgAge: {
$avg: '$age',
},
},
},
]
let result = db.collection('students').aggregate(query) // 计算 students 集合中所有学生的平均年龄
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
$max 计算最大值
js
function main() {
let query = [
{
$group: {
_id: null,
maxAge: {
$max: '$age',
},
},
},
]
let result = db.collection('students').aggregate(query) // 计算 students 集合中所有学生的最大年龄
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
$min 计算最小值
js
function main() {
let query = [
{
$group: {
_id: null,
minAge: {
$min: '$age',
},
},
},
]
let result = db.collection('students').aggregate(query) // 计算 students 集合中所有学生的最小年龄
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
一起使用
js
function main() {
let query = [
{
$group: {
_id: null,
count: { $sum: '$age' }, // 计算年龄总和
avgAge: { $avg: '$age' }, // 计算平均年龄
maxAge: { $max: '$age' }, // 计算最大年龄
minAge: { $min: '$age' }, // 计算最小年龄
},
},
]
let result = db.collection('students').aggregate(query) // 计算 students 集合中所有学生的年龄总和、平均年龄、最大年龄、最小年龄
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}
不同分组一起使用
js
function main() {
let query = [
{
$group: {
_id: '$name',
avgAge: { $avg: '$age' },
minAge: { $min: '$age' },
maxAge: { $max: '$age' },
count: { $sum: 1 }, // 计算相同姓名的数量
},
},
{
$group: {
_id: null,
totalStudents: { $sum: '$count' },
avgAge: { $avg: '$avgAge' },
minAge: { $min: '$minAge' },
maxAge: { $max: '$maxAge' },
},
},
]
let result = db.collection('students').aggregate(query) // 计算 students 集合中所有学生的年龄总和、平均年龄、最大年龄、最小年龄
if (result == null) {
return '查询失败'
}
return '查询成功:' + JSON.stringify(result)
}