group,aggregate,mapReduce

分组统计: group()
简单聚合: aggregate()
强大统计: mapReduce() db.collection.group(document)
document:{
key:{key1:1,key2:1}, //根据那几个字段分组
cond:{}, //筛选的条件
reduce: function(curr,result) { //分组之后的聚合运算,curr是一行数据,result是计算后的结果
},
initial:{}, //初始化result里面
finalize:function() { //reduce一组都执行完毕后最后执行的函数
}
} #计算每个栏目下(cat_id)的商品数 count()操作
select cat_id,count(*) from goods group by cat_id; //mysql操作 use shop
db.goods.group(
{
key:{cat_id:1}, //根据哪个字段分组
cond:{}, //所有行取出来,不加条件
reduce:function(curr,result) {//reduce的执行过程:每一行就是一个curr,每一组共用一个result变量,
result.cnt += 1; //result.cnt是每组有多少行,每个组有一个result,
},
initial:{cnt:0}
}
):
[
{
"cat_id" : 4.0,
"cnt" : 3.0
},
{
"cat_id" : 8.0,
"cnt" : 3.0
},
{
"cat_id" : null,
"cnt" : 2.0
}
] #查询每个栏目下价格高于3500元的商品数量
use shop
db.goods.group(
{
key:{cat_id:1}, //cat_id分组,并且查出car_id和shop_price字段
cond:{shop_price:{$gt:3500}},
reduce:function(curr,result) {
result.cnt += 1;
},
initial:{cnt:0}
}
):
[
{
"cat_id" : 3.0,
"shop_price" : 5999.0,
"cnt" : 1.0
},
{
"cat_id" : 5.0,
"shop_price" : 3700.0,
"cnt" : 1.0
}
] #查询每个栏目下价格大于3000元的商品个数
{
key:{cat_id:1},
cond:{},
reduce: function(curr,result) {
result.total += 1;
},
initial:{total:0}
}:
[
{
"cat_id" : 4.0,
"total" : 3.0
},
{
"cat_id" : 8.0,
"total" : 3.0
},
{
"cat_id" : null,
"total" : 2.0
}
] #计算每个栏目下的商品库存量 sum()操作
select sum(goods_number) from goods group by cat_id; use shop
db.goods.group(
{
key:{cat_id:1},
cond:{},
reduce: function(curr,result) {
result.total += curr.goods_number;
},
initial:{total:0}
}
):
[
{
"cat_id" : 4.0,
"total" : 3.0
},
{
"cat_id" : 8.0,
"total" : 61.0
},
{
"cat_id" : null,
"total" : NaN
}
] #查询每个栏目最贵的商品价格, max()操作
select max(shop_price) from goods group by cat_id; use shop
db.goods.group(
{
key:{cat_id:1},
cond:{},
reduce:function(curr , result) {
if(curr.shop_price > result.max) {
result.max = curr.shop_price;
}
},
initial:{max:0}
}
): #查询每个栏目下商品的平均价格
select cat_id,avg(shop_price) from goods group by cat_id; use shop
db.goods.group(
{
key:{cat_id:1}, //相当于group by
cond:{}, //相当于where
reduce:function(curr , result) { //相当于sum.avg函数
result.cnt += 1;
result.sum += curr.shop_price;
},
initial:{sum:0,cnt:0}, //进这个组执行一下
finalize:function(result) { //出这个组执行一下, 组操作完毕后的回调函数
result.avg = result.sum/result.cnt;
}
}
):
[
{
"cat_id" : 4.0,
"sum" : 6891.0,
"cnt" : 3.0,
"avg" : 2297.0
},
{
"cat_id" : 8.0,
"sum" : 226.0,
"cnt" : 3.0,
"avg" : 75.3333333333333
},
{
"cat_id" : null,
"sum" : NaN,
"cnt" : 2.0,
"avg" : NaN
}
] 注意:
1:group需要我们手写聚合函数的业务逻辑
2:group 不支持集群shard cluster, 无法分布式运算 3:分布式可以用 aggregate() (version2.2) ,
或者mapReduce() (version2.4) GROUP BY $group
HAVING $match
SELECT $project
ORDER BY $sort
LIMIT $limit
SUM() $sum
COUNT() $sum #查询每个栏目下的商品数量
select count(*) from goods group by cat_id; db.goods.aggregate(
[
{
$group:{
_id:"$cat_id", //根据cad_id分组
total:{$sum:1} //乘以1
}
}
]
):
{
"_id" : null,
"total" : -2.0
}
{
"_id" : 14.0,
"total" : -2.0
}
{
"_id" : 2.0,
"total" : -1.0
}
{
"_id" : 13.0,
"total" : -2.0
} #查询goods下有多少条商品,select count(*) from goods
[
{$group:{_id:null,total:{$sum:1}}}
];
{
"_id" : null,
"total" : 33.0
} #查询每个栏目下 价格大于3000元的商品个数
use shop
db.goods.aggregate(
[
{$match:{shop_price:{$gt:3000}}},
{$group:{_id:"$cat_id",total:{$sum:1}}}
]
):
{
"_id" : 5.0,
"total" : 1.0
}
{
"_id" : 3.0,
"total" : 2.0
} #查询每个栏目下 价格大于50元的商品个数
#并筛选出"满足条件的商品个数" 大于等于3的栏目
select cat_id,count(*) as cnt from goods where shop_price>3000 group by cat_id having cnt>=2 use shop
db.goods.aggregate(
[
{$match:{shop_price:{$gt:3000}}}, //放在group之前是where
{$group:{_id:"$cat_id",total:{$sum:1}}},
{$match:{total:{$gte:2}}} //放在group之后是having
]
):
{
"_id" : 3.0,
"total" : 2.0
} #查询每个栏目下的库存量
use shop
db.goods.aggregate(
[
{$group:{_id:"$cat_id" , total:{$sum:"$goods_number"}}}, //cat_id分组,goods_number求和,
]
):
{
"_id" : 5.0,
"total" : 8.0
}
{
"_id" : 15.0,
"total" : 2.0
} #查询每个栏目下的库存量,并按库存量排序
use shop
db.goods.aggregate(
[
{$group:{_id:"$cat_id" , total:{$sum:"$goods_number"}}},
{$sort:{total:1}} //1是升序
]
) #查询每个栏目下的库存量,并按库存量排序
use shop
db.goods.aggregate(
[
{$group:{_id:"$cat_id" , total:{$sum:"$goods_number"}}},
{$sort:{total:1}},
{$limit:3} //取前3个
]
):
{
"_id" : null,
"total" : 0
}
{
"_id" : 2.0,
"total" : 0.0
}
{
"_id" : 15.0,
"total" : 2.0
} #查询每个栏目的商品平均价格,并按平均价格由高到低排序
select cat_id ,avg(shop_price) as pj from goods group by cat_id order by pj desc limit 3 use shop
db.goods.aggregate(
[
{$group:{_id:"$cat_id" , avg:{$avg:"$shop_price"}}}, //car_id排序,shop_price求平均,
{$sort:{avg:-1}},
{$limit:3}
]
):
{
"_id" : 5.0,
"avg" : 3700.0
}
{
"_id" : 4.0,
"avg" : 2297.0
}
{
"_id" : 3.0,
"avg" : 1746.06666666667
}
mapReduce 随着"大数据"概念而流行,mapReduce的真正强项在于分布式。
其实mapReduce的概念非常简单,比aggregate要简单,从功能上说,相当于RDBMS(传统数据库)的 group 操作。 当数据非常大时,像google,有N多数据中心,数据都不在地球的一端,用group力所不及.group既然不支持分布式, 由于单台服务器的运算能力必然是有限的. 而mapRecuce支持分布式(不是算法好),而是支持大量的服务器同时工作,用蛮力来统计.mapRecuce就是group和aggregate,只不过支持分布式。 mapRecuce的工作过程:1.map-->映射,2.reduce->归约 map: 1.先在全世界机器找(分布式集群上找),把属于同一个组的数据,映射到一个数组上.cat_id [23,2,6,7],2.reduce: 把数组(同一组)的数据,进行运算. #用mapReduce计算每个栏目的库存总量 //map函数(进行映射工作,映射成一个二维数组)
var map = function() {
emit(this.cat_id,this.goods_number); //根据cat_id分组,
} /*
{
cat_id1:[goods_number1,goods_number2,goods_number3.....],
cat_id2:[goods_number1,goods_number2,goods_number3.....]
cat_id3:[goods_number1,goods_number2,goods_number3.....]
}
*/ var reduce = function(cat_id,numbers) { //对数组做处理,求goods_number的和,
return Array.sum(numbers); //mongo对js的数组增加的求和方法
} /*
{
_id:cat_id1, value:goods_number1+goods_number2+goods_number3.....,
_id:cat_id1, value:goods_number1+goods_number2+goods_number3.....,
_id:cat_id1, value:goods_number1+goods_number2+goods_number3.....,
}
*/ db.goods.mapReduce(map,reduce,{out:'res'}); //out计算的结果放在res集合里面去,
//多了一个res表
show tables
db.res.find():
{
"_id" : null,
"value" : NaN
}
{
"_id" : 2.0,
"value" : 0.0
}
{
"_id" : 3.0,
"value" : 203.0
}
{
"_id" : 4.0,
"value" : 3.0
}
{
"_id" : 15.0,
"value" : 2.0
} //查看array的所有方法:
for (var k in Array){
print(k)
}:
contains
unique
shuffle
tojson
fetchRefs
sum
avg
stdDev #用mapReduce计算每个栏目下商品的平均价格
var map = function() {
emit(this.cat_id,this.shop_price);
}
var reduce = function(cat_id,values) {
return Array.avg(values);
}
db.goods.mapReduce(map,reduce,{out:'res'});

{
"_id" : null,
"value" : NaN
}
{
"_id" : 2.0,
"value" : 823.33
}
{
"_id" : 3.0,
"value" : 1746.06666666667
}
var map = function() {
if(this.jing < 0 || this.wei < 0){
return;
}
var j = Math.floor(this.jing/5)*5;
var w = Math.floor(this.wei/5)*5;
var block = j+":"+w;
emit(block,1);
}
var reduce = function(block,values) {
return Array.sum(values);
}
db.goods.mapReduce(map,reduce,{out:'res'});

mongo14-----group,aggregate,mapReduce的更多相关文章

  1. 72.Python中ORM聚合函数详解:Avg,aggregate,annotate

    聚合函数: 如果你用原生SQL语句,则可以使用聚合函数提取数据.比如提取某个商品销售的数量,那么就可以使用Count,如果想要知道销售的平均价格,那么就可以使用Avg. 聚合函数是通过aggregat ...

  2. scala - fold,aggregate,iterator

    import org.json4s._ import org.json4s.jackson._ import org.json4s.jackson.JsonMethods._ import org.j ...

  3. MongoDB常用查询,排序,group,SpringDataMongoDB update group

    MongoDB查询 指定查询并排序 db.getCollection('location').find({"site.id":"川A12345","s ...

  4. 大数据学习----day27----hive02------1. 分桶表以及分桶抽样查询 2. 导出数据 3.Hive数据类型 4 逐行运算查询基本语法(group by用法,原理补充) 5.case when(练习题,多表关联)6 排序

    1. 分桶表以及分桶抽样查询 1.1 分桶表 对Hive(Inceptor)表分桶可以将表中记录按分桶键(某个字段对应的的值)的哈希值分散进多个文件中,这些小文件称为桶. 如要按照name属性分为3个 ...

  5. 关于Hive的调优(本身,sql,mapreduce)

    1.关于hive的优化 ->大表拆分小表 ->过滤字段 ->按字段分类存放 ->外部表与分区表 ->外部表:删除时只删除元数据信息,不删除数据文件 多人使用多个外部表操作 ...

  6. 多路径配置vlome group共享存储,VG的更新。

    1.  PV的概念: a)        一块物理磁盘一块物理硬盘在被LVM管理时被称为“物理卷”. b)        在LVM能对其进行管理之前需要在硬盘上产生一些特殊的数据结构,这个过程就是建立 ...

  7. MapReduce,DataJoin,链接多数据源

    主要介绍用DataJoin类来链接多数据源,先看一下例子,假设二个数据源customs和orders customer ID       Name      PhomeNumber 1         ...

  8. Linux - 有效群组(effective group)与初始群组(initial group),groups,newgrp

    每个使用者在他的 /etc/passwd 里面的第四栏有所谓的 GID ,那个 GID 就是所谓的『初始群组 (initial group) 』!也就是说,当用户一登陆系统,立刻就拥有这个群组的相关权 ...

  9. GROUP BY你都不会!ROLLUP,CUBE,GROUPPING详解

    Group By Group By 谁不会啊?这不是最简单的吗?越是简单的东西,我们越会忽略掉他,因为我们不愿意再去深入了解它. 1 小时 SQL 极速入门(一) 1 小时 SQL 极速入门(二) 1 ...

随机推荐

  1. POJ 1201 Intervals(差分约束 区间约束模版)

    关于差分约束详情可阅读:http://www.cppblog.com/menjitianya/archive/2015/11/19/212292.html 题意: 给定n个区间[L,R], 每个区间至 ...

  2. vs2017编译boost 1.70.0

    目前最新版本的boost库是1.70.0.现在在学习使用cinatra搭建c++的http服务器,需要用到boost库中的asio,下载了一下最新版本的boost库,捣鼓了半天. 1.下载 boost ...

  3. CI 安装时目录的安全处理

    如果你想通过隐藏 CodeIgniter 的文件位置来增加安全性,你可以将 system 和 application 目录修改为其他的名字,然后打开主目录下的 index.php 文件将 $syste ...

  4. 大数据学习——hadoop集群搭建2.X

    1.准备Linux环境 1.0先将虚拟机的网络模式选为NAT 1.1修改主机名 vi /etc/sysconfig/network NETWORKING=yes HOSTNAME=itcast ### ...

  5. ORACLE-023:令人烦恼的 ora-01722 无效数字

    https://blog.csdn.net/yysyangyangyangshan/article/details/51762746

  6. Linux(Centos6.5)+Nginx+PHP-fpm+Mysql配置

    第一步:准备安装包 1.从[](http://nginx.org/en/download.html).下载nginx 源码包 //NOTE! 下载稳定版本 2.从[](http://php.net/d ...

  7. BGP表

    BGP是一种基于策略的路由选择协议,让AS能够根据多种BGP属性来控制数据流的传输.运行BGP的路由器交换被称为路径矢量或者属性的NLRI.路径矢量信息中包含一个BGP-AS号列表称为AS-PATH属 ...

  8. BZOJ 3175: [Tjoi2013]攻击装置

    捉水题真是捉上瘾了TUT Description 给定一个01矩阵,其中你可以在0的位置放置攻击装置.每一个攻击装置(x,y)都可以按照“日”字攻击其周围的 8个位置(x-1,y-2),(x-2,y- ...

  9. [转]Android SDK下载和更新失败的解决方法

    今天更新sdk,遇到了更新下载失败问题: Fetching https://dl-ssl.google.com/android/repository/addons_list-2.xmlFetched ...

  10. 使用Navicat进行数据库对比同步

    使用Navicat进行数据库对比同步 当有多个数据库时,有时会出现结构或者数据不同步的问题,这时候可以使用navivat工具对比同步( 我的Navicat版本是11.0.17). 参考博客: 岁伏的博 ...