【问题标题】:Iterate over array and calculate average values of array-parts遍历数组并计算数组部分的平均值
【发布时间】:2011-07-21 15:10:01
【问题描述】:

我有一个这样的数组:

["2011-06-16 16:37:20",23.2],
["2011-06-21 16:37:20",35.6],
["2011-06-26 16:37:20",41.8],
["2011-07-01 16:37:20",25],
["2011-07-06 16:37:20",22.8],
["2011-07-11 16:37:20",36.4],
["2011-07-16 16:37:20",34],
["2011-07-21 16:37:20",20]
[...]

Format: [$date,count]

现在我需要为每个数组元素添加第三个和第四个值,这是之前或之后 N 个计数的平均值。

N=3 时的示例

第 3 个值应该是之前 3 个计数值的平均值,第 4 个值应该是当前数组元素之后的 3 个计数值的平均值。 结果如下所示:

["2011-06-16 16:37:20",23.2, null,  34.13],
["2011-06-21 16:37:20",35.6, null,  29.86],
["2011-06-26 16:37:20",41.8, null,  28.06],
["2011-07-01 16:37:20",25,   33.53, 31.06],
["2011-07-06 16:37:20",22.8, 34.13, 30.13],
["2011-07-11 16:37:20",36.4, 29.86, null],
["2011-07-16 16:37:20",34,   28.06, null],
["2011-07-21 16:37:20",20,   31,06, null]

null 值只不过是无法计算的值的占位符,因为没有足够的值来计算 N 计数的平均值。 也可以放置所有可用计数的平均值,例如第三行的“24.4”(23.2+35.6)/2 而不是null

["2011-06-26 16:37:20",41.8, 24.4,  28.06],

我不知道,如何构建代码。

希望得到提示或帮助。

谢谢。

//更新:对不起,但是..请:有人可以解释一下,为什么有 2 个人对这个问题投了反对票?我不知道为什么。这不公平 - 跟我说话,如果我做错了? 对不起!

【问题讨论】:

  • 你真的应该尝试自己做这件事,然后就给你带来麻烦的事情寻求具体的帮助。要求社区为您编写它并不是这个网站的全部目的......
  • 抱歉,我试了 3 个小时 - 但不知道。遍历数组不是问题,但是我不知道如何获取当前之前的n个值和之后的n个值。
  • 尝试实现一个 N=1 的解决方案 - 即,仅平均这个数字和之前的数字。然后尝试 N=2 看看是否出现了模式。
  • @The Bndr:贴出你试过的代码!最好的学习方法是让别人指出你方法的问题;否则,在没有真正理解的情况下使用别人的解决方案太诱人了。
  • @The Bndr - 投票结束是因为这不是您以外的任何人都可能关心的问题。这是一个非常具体的问题。也就是说,我很无聊,所以我添加了一个解决方案。

标签: javascript arrays average


【解决方案1】:

使用各种高阶函数的解决方案:

var arrs = [
    ["2011-06-16 16:37:20",23.2],
    ["2011-06-21 16:37:20",35.6],
    ["2011-06-26 16:37:20",41.8],
    ["2011-07-01 16:37:20",25],
    ["2011-07-06 16:37:20",22.8],
    ["2011-07-11 16:37:20",36.4],
    ["2011-07-16 16:37:20",34],
    ["2011-07-21 16:37:20",20]];

function avg(arr) {
    return (arr.reduce(function(acc, el, i) {
        return el + acc;
    }, 0) / arr.length).toFixed(2) * 1;
}

function visit(acc, el, i, arr) {
    el.push((acc.length >= 3) ? avg(acc) : null);
    acc[i % 3] = el[1];
    return acc;
}

arrs.reduce(visit, []);
arrs.reverse().reduce(visit, []);
arrs.reverse();

结果:

[["2011-06-16 16:37:20", 23.2, null, 34.13], 
 ["2011-06-21 16:37:20", 35.6, null, 29.87], 
 ["2011-06-26 16:37:20", 41.8, null, 28.07], 
 ["2011-07-01 16:37:20", 25, 33.53, 31.07], 
 ["2011-07-06 16:37:20", 22.8, 34.13, 30.13], 
 ["2011-07-11 16:37:20", 36.4, 29.87, null], 
 ["2011-07-16 16:37:20", 34, 28.07, null], 
 ["2011-07-21 16:37:20", 20, 31.07, null]]

【讨论】:

  • 感谢您发布的解决方案。花了几分钟,直到我明白那里发生了什么,这段代码是如何工作的。但是现在,我理解了这段代码。迭代数组两次,第二次反向运行,是一种实践,我从未想过。伟大的!非常感谢。
【解决方案2】:
arrays = [
    ["2011-06-16 16:37:20",23.2],
["2011-06-21 16:37:20",35.6],
["2011-06-26 16:37:20",41.8],
["2011-07-01 16:37:20",25],
["2011-07-06 16:37:20",22.8],
["2011-07-11 16:37:20",36.4],
["2011-07-16 16:37:20",34],
["2011-07-21 16:37:20",20]
];
arrays.forEach(function(el,i,theArray){
    var a=null,b=null;
    if(i > 2){
        a = (theArray[i-3][1] + theArray[i-2][1] + theArray[i-1][1]) / 3;
        a = a.toPrecision(a.toString().indexOf('.') != -1 ? 2+a.toString().indexOf('.') : a.toString().length);
    }
    if(i < theArray.length - 3){
        b = (theArray[i+3][1] + theArray[i+2][1] + theArray[i+1][1]) / 3;
        b.toPrecision(b.toString().indexOf('.') != -1 ? 2+b.toString().indexOf('.') : b.toString().length);
    }
    el.push(a);
    el.push(b);
});

【讨论】:

  • 感谢您的回答和您的时间,您花在了该解决方案上。不幸的是,我只能将一个答案标记为正确 - 所以我将采用 lwburk 的解决方案,它看起来更紧凑和健壮。谢谢。
猜你喜欢
  • 2017-06-30
  • 1970-01-01
  • 1970-01-01
  • 2018-10-15
  • 2017-08-22
  • 2021-07-19
  • 2014-05-14
  • 2013-10-25
相关资源
最近更新 更多