WD1X.COM - 问答一下,轻松解决,电脑应用解决专家
主板显卡CPU内存显示器
硬盘维修显卡维修显示器维修
系统注册表系统命令DOSWin8
存储光存储键盘鼠标
内存维修打印机维修
WinXPVistaWin7linux
硬件综合机箱电源/散热器手机数码
主板维修CPU维修键鼠维修网页设计
办公教程ExcelWordPowerPointWPS
网络工具系统工具图像工具
PS教程数据库局域网服务器
PHP教程CSSjavascriptXML

mongodb使用aggregate、group、match实现mysql中的having(count(1)>1)的功能

更新时间:2021-05-12 11:51 作者:selectgo点击:
关系型数据库中分组去重一般都是group by … having(count(1)>1)…赛选出来重复的记录组,然后一条sql搞定,但是在mongodb里面,没有这么方便了,需要自己写脚本来实现,可以通过aggregate、group、match来操作处理。
 
1,准备录入测试数据
db.stu.insert({cid:1,age:14,name:'gom1'});
db.stu.insert({cid:1,age:12,name:'jack2'});
db.stu.insert({cid:2,age:13,name:'Lily3'});
db.stu.insert({cid:2,age:14,name:'tony4'});
db.stu.insert({cid:2,age:9,name:'Harry5'});
db.stu.insert({cid:2,age:13,name:'Vincent6'});
db.stu.insert({cid:1,age:14,name:'bill7'});
db.stu.insert({cid:2,age:17,name:'tim8'});
db.stu.insert({cid:1,age:10,name:'bruce9'});
db.stu.insert({cid:3,age:20,name:'luxi10'});
 
执行窗口显示如下:
 
mongos> use test;
switched to db test
mongos> 
mongos> db.stu.insert({cid:1,age:14,name:'gom1'});
mongos> db.stu.insert({cid:1,age:12,name:'jack2'});
mongos> db.stu.insert({cid:2,age:13,name:'Lily3'});
mongos> db.stu.insert({cid:2,age:14,name:'tony4'});
mongos> db.stu.insert({cid:2,age:9,name:'Harry5'});
mongos> db.stu.insert({cid:2,age:13,name:'Vincent6'});
mongos> db.stu.insert({cid:1,age:14,name:'bill7'});
mongos> db.stu.insert({cid:2,age:17,name:'tim8'});
mongos> db.stu.insert({cid:1,age:10,name:'bruce9'});
mongos> db.stu.insert({cid:3,age:20,name:'luxi10'});
 
2,开始分组测试,按照cid进行分组
2.1,先统计分组记录数
var group=([
{KaTeX parse error: Expected '}', got 'EOF' at end of input: group:{_id:"cid", max_age: {m a x : " max:"max:"age"},count: { KaTeX parse error: Expected 'EOF', got '}' at position 8: sum: 1 }̲}}, {sort:{count:-1}}
])
执行窗口如下:
 
mongos> var group=([    
...      {$group:{_id:"$cid", max_age: {$max:"$age"},count: { $sum: 1 }}},
...      {$sort:{count:-1}}
... ])
mongos>
 
2.2,定义就是找出存在重复的分组,使用管道操作符m a t c h , 条 件 是 普 通 查 询 的 格 式 , 但 是 作 用 于 match,条件是普通查询的格式,但是作用于match,条件是普通查询的格式,但是作用于group的输出结果的格式:
var match ={“KaTeX parse error: Expected '}', got 'EOF' at end of input: …":{"count" : {"gt” : 1}}};
执行窗口如下:
 
mongos> var match ={"$match":{"count" : {"$gt" : 1}}};
mongos>
 
3 获取数据
mongos> db.stu.aggregate(group, match);
{
"result" : [
{
"_id" : 2,
"max_age" : 17,
"count" : 5
},
{
"_id" : 1,
"max_age" : 14,
"count" : 4
},
{
"_id" : 3,
"max_age" : 20,
"count" : 1
}
],
"ok" : 1
}
mongos> 
 
PS:这里match无效,出来count为1的数据,没有match成功,问题在哪里呢?
 
网友Traveller的指点:
db.stu.aggregate(group, match); 看出来了吗?你这样调用相当于把match作为options传进去了,当然没有用,这种方法得不到最终的数据,因为每个管道是数组的一个元素,而group单独是一个数组,match是一个元素。除非把它加进数组里面,看如下写法,
group.push(match);
db.stu.aggregate(group);
 
然后自己去看官网进一步研究:
http://docs.mongoing.com/manual-zh/reference/method/db.collection.aggregate.html#db.collection.aggregate,查看了aggregate介绍,aggregate的方法签名是function (pipeline, aggregateOptions),
第一个参数是piplines,所有的对数据的判断条件都应该在这里面。
第二个参数是options,指定查询时候使用的一些选项。
The options document can contain the following fields and values:包括explain、allowDiskUse、cursor,所以我传入的match是针对group的判断条件,所以不能作为第二个参数,而应该放到第一个参数里面去,所以需要用到group的push功能,将match加入第一个参数里面去才能使count>1的判断生效。
 
4,使用group的push功能
mongos> group.push(match);
3
mongos> db.stu.aggregate(group);
{
"result" : [
{
"_id" : 2,
"max_age" : 17,
"count" : 5
},
{
"_id" : 1,
"max_age" : 14,
"count" : 4
}
],
"ok" : 1
}
mongos> 
 
看到已经过滤掉了count=1的记录组了,表示push成功了。
顶一下
(0)
0%
踩一下
(0)
0%
------分隔线----------------------------
你可能感兴趣的内容