在mongo-shell中执行mapreduce时出错

时间:2013-05-23 15:45:55

标签: javascript mongodb mapreduce mongo-shell

发生以下错误

Thu May 23 07:14:53.437 JavaScript execution failed: map reduce failed:{
    "errmsg" : "exception: JavaScript execution failed: TypeError: Cannot read property 'product_category' of undefined near '(values[i].product_category)'  (line 21)",
    "code" : 16722,
    "ok" : 0
 at src/mongo/shell/collection.js:L970

我的地图和缩小功能是:

map1 = function()
{ 
   emit({Product_id:this.Product_id
}, 
{
   product_category:this.product_category
}); 
}

reduce1 = function(key, values)
{
var ref = new Array();
var count = 0;
var tmp="";
var pdt_array = new Array();
for (var i = 1; i <= values.length; i++) {                                 
if( i == 1 )
{
     pdt_array_array[i] = values[i];
} 
else
{                     
    tmp = values[i];
    while(i > 1)
    {
        if(tmp == pdt_array[i])
        {
            ref.push(values[i].product_category);
            count++;
        }
        i--;

    }
    pdt_array[i] = tmp;
    tmp = "";
}
}
   return {product_category:ref, Count:count}
}

db.DummyReverse.mapReduce(map1, reduce1, {out:{reduce:"product_count_while"}})

2 个答案:

答案 0 :(得分:2)

问题是您没有从reduce函数返回相同的格式,因为您作为值发布。由于reduce函数可以被称为0,每个键一次或多次,你必须在所有这些情况下使用完全相同的格式,你不能假设你的reduce函数只会被调用一次。

答案 1 :(得分:0)

Javascript数组是0索引的。所以你最后的for-run想要访问一个不存在的数组索引。我希望我能正确理解你的代码。

[...]

for (var i = 0; i < values.length; i++) {                                 
    if ( i == 0) {
         pdt_array_array[i] = values[i];
    } else {                     
        tmp = values[i];

        while(i > 0) {
            if(tmp == pdt_array[i]) {
                ref.push(values[i].product_category);
                count++;
            }

            i--;
        }

        pdt_array[i] = tmp;
        tmp = "";
    }
}

[...]

注意for (var i = 0; i < values.length; i++)。所以第n个元素的索引为n-1。最后一个元素length-1

备注:你确定没有无限循环,for循环增加i并且在减少它的同时减少它吗?