不知道大家有没有遇到过,使用mapreduce其中需要计数记录数的时候,我们在reduce中使用 number = number + 1 发现统计的出来的数量往往小于我们希望的结果。在此小编也遇到同样的问题,那么mapreduce如何实现计数呢,首先我们看下mapreduce的基本语法:
db.runCommand(
{ mapreduce : 字符串,集合名,
map : 函数,见下文
reduce : 函数,见下文
[, query : 文档,发往map函数前先给过渡文档]
[, sort : 文档,发往map函数前先给文档排序]
[, limit : 整数,发往map函数的文档数量上限]
[, out : 字符串,统计结果保存的集合]
[, keeptemp: 布尔值,链接关闭时临时结果集合是否保存]
[, finalize : 函数,将reduce的结果送给这个函数,做最后的处理]
[, scope : 文档,js代码中要用到的变量]
[, jsMode : 布尔值,是否减少执行过程中BSON和JS的转换,默认true]
//注:false时 BSON-->JS-->map-->BSON-->JS-->reduce-->BSON,可处理非常大的mapreduce,
//true时BSON-->js-->map-->reduce-->BSON
[, verbose : 布尔值,是否产生更加详细的服务器日志,默认true]
}
);看到number了么,number在map中使用 1 作为它的固定的value
//map示例
$map = 'function(){
var key = {
advert_id : this.advert_id,
district_code : this.district_code
};
var values = {
amount: this.amount,
number: 1,
advertiser_id: this.advertiser_id
};
emit(key, values);
}';接下来在reduce中使用 values[i].number;来计数即可
//reduce示例
$reduce = 'function(key, values){
var result = {amount:0, number:0, advertiser_id:0};
for(var i in values) {
result.advertiser_id = values[i].advertiser_id;
result.amount += values[i].amount;
result.number += values[i].number;//注意:数量统计时,不是这里+1即可,需要通过
//values[i].number来赋值
}
return result;
}';
$query = null;总结:使用MapReduce时,尽量只用到累加、累减、累乘等基本操作,不要去用++、push、delete等可能会产生风险的操作