1. 聚合
1.1 聚合概念
MongoDB的一次聚合操作就是对一个表进行多个工序的加工,其中的每个工序都可以修改、增加、删除文档,最终产出我们需要的数据集合
MongoDB提供了3种方式来执行聚合命令:聚合管道方法、 map-reduce方法和单目标聚合方法。
1.2 聚合管道方法
聚合管道方法又可以直接理解为合计流水线法,就是把集合里若干含数值型的文档记录,其键对应的值进行各种分类统计。
该方法支持分片集合操作
//语法
db.collection_name.aggregate(
[{
$match: {<field>}
},//统计查找条件
{
$group:{<fieldl>,<field2>}
}/*field1为分类字段;field2为含各种统计操作符的数值型字段,如$sum、$avg、$min、$max、$push、$addToSet、$first、$last操作符*/
])
//案例
use goodsdb
db.Sale_detail.insert (
[
{goodsid:"1001", amount:2, price:10.2, ok:false} ,
{goodsid:"1001", amount:3, price:14.8, ok:false} ,
{goodsid:"1002", amount:10,price:50, ok:false} ,
{goodsid:"1002", amount:2, price:10, ok:true}
]
)
db.Sale_detail.aggregate(
[
{
$match:{ok:false}
//查找条件:ok为false的文档
},
{
$group:{_id:"$goodsid",total:{$sum:"$amount"}}
//按goodsid分类统计amount字段的总数量
//_id:必须指定唯一性字段;$goodsId:分类字段名称
//total:统计结果字段名;$sum:求和操作符;$amout求和字段:必须加双引号
}
]
)
//案例:请查出persons中每个国家学生数学成绩最好的学生信息(必须在90以上)
db.persons.aggregate([{$match:{m:{$gte:90}}},{$group:{_id:"$country",value:{$sum:"$m"}}}])
1.3 map-reduce方法
map部分:
- 作用:用于分组的。
- emit(param1, param2)
- param1:需要分组的字段,this.字段名
- param2:需要进行统计的字段,this.字段名
reduce部分:
- 作用:处理需要统计的字段
- var reduce = function(key, values){…统计字段处理}
- key: 指分组字段(emit的param1)对应的值
- values:指需要统计的字段(emit的param2)值组成的数组
options部分:
- { query: { age: {$lt: 25} }, out: “name_totals” }
- query:先筛选符合条件的记录出来,再进行分组统计
- out:将分组统计后的结果输出到哪个集合当中。默认情况下,out所指定的集合在数据库断开连接后再次打开时,依旧存在,并保留之前的所有记录的
执行分组统计部分:
- db.集合名.mapReduce( map, reduce, options )
先在集合中插入一些数据:
//需求1:统计不同地方('Guangzhou,Beijing,Shanghai')的人的岁数总和
var map = function(){ emit(this.location, this.age); }
var reduce = function( key, values ){ return Array.sum(values); }
var options = { out: "age_totals" }
db.mythings.mapReduce( map, reduce, options )
//需求2:统计不同地方(‘Guangzhou,Beijing,Shanghai’)的人数总和
var map = function(){ emit(this.location, 1); }
var reduce = function( key, values ){ return Array.sum(values); }
var options = { out: "person_totals" }
db.persons.mapReduce( map, reduce, options )
//需求3:统计不同地方(‘Guangzhou,Beijing,Shanghai’)的人名列表
var map=function(){ emit(this.location, this.name); }
var reduce=function( key, values){ return values.join(', '); }
var options = { out: "name_totals" }
db.mythings.mapReduce( map, reduce, options )
//需求4:统计不同地方('Guangzhou,Beijing,Shanghai'),并且年龄在25岁(不包括25岁)以下的人名列表
var map = function(){ emit(this.location, this.name); }
var reduce = function(key,values){return key + ':' + values.join(',');}
var options = { query: { age:{$lt: 25} }, out: "name_totals" }
db.mythings.mapReduce( map, reduce, options )
1.4 单一目标聚合方法
该方法下,目前有两种聚合操作功能:
- count:返回匹配查询结果的数量
- dstinct:返回指定某个字段非重复值的列表
//count()
//案例:请查询persons中美国学生的人数
db.persons.find({country:"USA"}).count()
//distinct
//案例:请查询出persons中一共有多少个国家分别是什么
db.runCommand({distinct:"persons",key:"country"}).values
2. 复制
MongoDB数据库在实际生产环境下,多数基于多服务器集群运行,并进行相应的数据分布式处理。因此,必须考虑数据读写的可用性和安全性,如一台服务器出故障时,该能保证MongoDB数据处理的正常进行。
复制就是为解决上述问题而产生的,通过复制功能可以实现多服务器的数据冗余备份操作;使备份数据的服务器具备额外提供独立读访问请求的功能(分布式读取数据 ,可以解决高井发客户端读用户访问问题);当服务器出故障时,提供自动故障转移、自动数据恢复。
部署过程:
- 安装主节点MongoDB安装包。
- 用replset命令选项指定副本集名称。
- 安装从节点集群。
- 设置集群配置文件。
- 将其他成员添加到副本集里。
- 检查副本集状态。
复制作用:
- 保障数据的安全性
- 数据高可用性
- 灾难恢复
- 无需停机维护(如备份,重建索引,压缩)
- 分布式读取数据
3. 分片
分片是指将数据拆分将其分散存放在不同的器上的过程,有时也用分区来表示这个概念。
Mongodb数据库分片技术对大数据集和高吞吐量操作提供很好的部署支持功能
当单机无法很好地满足大数据存储及读写应用要求 ,就可考虑采用多服务器分布式数据处理的分片技术了。
分片的作用:
- 使用分片减少了每个分片需要处理的请求数,因此,通过水平扩展,群集可以提高自己的存储容量
- 使用分片减少了每个分片存储的数据
- 分片的优势在于提供类似线性增长的架构,提高数据可用性,提高大型数据库查询服务器的性能