使用Doctrine

时间:2016-03-31 10:32:12

标签: mongodb doctrine-orm mapreduce doctrine

我使用mongo查询来计算每个项目的总价。 我的查询看起来像是

$ queryBuilder = new Query \ Builder($ this,$ documentName);

$queryBuilder->field('created')->gte($startDate);
$queryBuilder->field('is_test_value')->notEqual(true);
..........
$queryBuilder->map('function() {emit(this.item, this.price)}');
$queryBuilder->reduce('function(item, valuesPrices) {
    return {sum: Array.sum(valuesPrices)}
}');

这样可行,没问题。但我发现在某些情况下(200个结果中大约20个案例)我在字段sum中得到了奇怪的结果 - 而不是总和值我看到像

这样的结构

[objectObject]444444444444444

4 - 是商品的价格。

我尝试将reduce块替换为阻塞,如下所示:

    var sum = 0;
    for (var i = 0; i < valuesPrices.length; i++) {
        sum += parseFloat(valuesPrices[i]);
    }
    return {sum: sum}

在这种情况下,我会看到NAN值。

我怀疑字段price中的某些数据插入不正确(不是浮点数,而是字符串,对象等)。我尝试从mongo cli执行我的查询,我发现所有价格值都是整数。

1 个答案:

答案 0 :(得分:2)

它不是&#34;奇怪&#34;一点都不你"broke the rules",现在你付钱了。

  
      
  • &#34; MongoDB可以为同一个密钥多次调用reduce函数。在这种情况下,该键的reduce函数的先前输出将成为该键的下一个reduce函数调用的输入值之一。&#34;
  •   

mapReduce的主要规则(如上所述)是必须从&#34; reducer&#34;中返回完全相同的结构就像你从&#34; mapper&#34;那样。这是因为&#34;减速机&#34;实际上可以为同一个&#34;键&#34;运行几次。这就是mapReduce处理大型列表的方式。

你可以通过返回一个奇异值来解决这个问题,就像你在emit:

中做的那样
return Array.sum(values);

然后就不会有问题了。添加一个对象键使得数据不一致,因此当&#34;减少&#34;时会出现错误。结果被反馈到&#34;减速器&#34;试。