mongoose的aggregate聚合管道中的$match,$skip,$limit,$lookup,$project,$unwind,$group,$sort使用方法

tech2022-07-05  149

聚合管道是链式调用,上面的处理结果会用作下次处理初始值

1.$match

可以看做筛选,就是查找符合条件的数据

// 查找user_id=user_id的数据 { $match: { user_id: ObjectId(user_id) } } // 查找array里包含的user_id的数据 { $match: { user_id: { $in: array } } }

2. $skip和 $limit

这两个是做翻页用的

// page->第几页 size->每页多少个 [ { $skip: (Number(page) - 1) * Number(size) }, { $limit: Number(size) } ]

3.$lookup

表与表关联查询 如:我在a表存了b表的id,也就是a里有一个 b_id 字段 a表

{ _id: "....", b_id: "aaaaa", name: "这是a" ...... }

b表

{ _id: "aaaaa", name: "这是b" } a.aggregate([ { $lookup: { from: 'bs',// 要查询的表(带s是因为mongodb表自动加s,这里的名字必须是真正的表名) localField: 'b_id',// 根据什么字段,这里是a里的b_id foreignField: '_id',// 要匹配的字段,找b里面_id=b_id的数据 as: 'b_data'// 放入的字段 } } ])

结果

{ _id: "....", b_id: "aaaaa", name: "这是a", b_data: { _id: "aaaaa", name: "这是b" } ...... }

4.$sort

排序

// 根据创建时间倒序 { $sort: { created_at: -1 } }

5.$unwind

将一个数组字段拆分成多个 值

{ name: "parent", children: [ { name: "child1" }, { name: "child2" } ] } { $unwind: "$children" }

结果

[ { name: "parent", children: { name: "child1" } }, { name: "parent", children: { name: "child2" } } ]

6.$project

控制值得显示,重命名,还有加减乘除等操作(着实有点多,脑壳疼) 模拟数据

{ "state": -1, "sort": 1, "is_delete": 0, "_id": "5f4907f1984fd26e900ec8e8", "name": "总经理", "created_at": "2020-08-28T13:34:41.282Z", "update_at": "2020-08-28T13:34:41.282Z", "__v": 0 } // 只显示sort和name。(0是不显示,1是显示,_id不写默认显示) aggregate([ { $project : { _id: 0, sort : 1 , name : 1 }} ]) // 把name换成positionName显示 aggregate([ { $project : { _id: 0, sort : 1 , positionName : "$name" }} ]) // sort输出的值乘2 // 加法($add)、减法($subtract)、乘法($multipy)、除法($divide) aggregate([ { $project : { _id: 0, sort : { "$multipy": [ "$sort",2 ] } , positionName : "$name" }} ]) // 还可以进行逻辑输出,关系运算,逻辑运算,字符操作等(如将两个字符连接成一个)

7.$group

给数据分组计算 模拟数据

{ "item" : "aaa", "price" : 10, "quantity" : 2, "date" : ISODate("2014-03-01T08:00:00Z") }, { "item" : "bbb", "price" : 20, "quantity" : 1, "date" : ISODate("2014-03-01T09:00:00Z") }, { "item" : "ccc", "price" : 5, "quantity" : 10, "date" : ISODate("2014-03-15T09:00:00Z") }, { "item" : "ccc", "price" : 5, "quantity" : 20, "date" : ISODate("2014-04-04T11:21:39.736Z") }, { "item" : "aaa", "price" : 10, "quantity" : 10, "date" : ISODate("2014-04-04T21:23:13.331Z") }

根据item进行分类,并且统计数量放入count

[ { $group : { _id : "$item",// 要进行合并的字段,前面的_id是必须的可以为空(不能改真的恶心) count: { $sum : 1} } } ]

结果

[ {_id:aaa:count:2}, {_id:bbb:count:1}, {_id:ccc:count:2} ]

求price的和 与 quantity平均数

{ $group : { _id : "$item", total: { $sum : "$price"}, avg: { $avg: "$quantity" } } }

更多的运算

$max 最大值 $min 最小值 $first 第一个值 $last 最后一个值

按月,日和年对文档进行分组

{ $group : { _id : { month: { $month: "$date" }, day: { $dayOfMonth: "$date" }, year: { $year: "$date" } }, // [ "$price", "$quantity" ] 指的是操作这两个数据,$multiply 对多个字段进行求和操作 totalPrice: { $sum: { $multiply: [ "$price", "$quantity" ] } } } }

将属于同一个item的price放入prices数组(会重复)

{ $group : { _id : "$item", prices: { $push: "$price" } } }

下面是不会重复写法

{ $group : { _id : "$item", prices: { $addToSet: "$price" } } }

通过item分类将整条数据放入数组

{ $group : { _id : "$item", arr: { $push: "$$ROOT" } } }

8.$facet

可以理解为创建多个管道

{ $facet: { <outputField1>: [ <stage1>, <stage2>, ... ], <outputField2>: [ <stage1>, <stage2>, ... ], ... } }
最新回复(0)