数组总和和平均值

jon*_*ler 152 javascript arrays average

我在添加数组的所有元素以及平均它们时遇到了问题.我该怎么做并用我目前的代码实现它?应该定义元素,如下所示.

<script type="text/javascript">
//<![CDATA[

var i;
var elmt = new Array();

elmt[0] = "0";
elmt[1] = "1";
elmt[2] = "2";
elmt[3] = "3";
elmt[4] = "4";
elmt[5] = "7";
elmt[6] = "8";
elmt[7] = "9";
elmt[8] = "10";
elmt[9] = "11";

// Problem here
for (i = 9; i < 10; i++){
  document.write("The sum of all the elements is: " + /* Problem here */ + " The average of all the elements is: " + /* Problem here */ + "<br/>");
}   

//]]>
</script>
Run Code Online (Sandbox Code Playgroud)

Ser*_*lla 447

我认为更优雅的解决方案:

var sum, avg = 0;

// dividing by 0 will return Infinity
// arr must contain at least 1 element to use reduce
if (arr.length)
{
    sum = arr.reduce(function(a, b) { return a + b; });
    avg = sum / arr.length;
}

document.write("The sum is: " + sum + ". The average is: " + avg + "<br/>");
Run Code Online (Sandbox Code Playgroud)

  • 使用累积移动平均线,你可以在reduce函数中完成所有操作(不需要`sum/times.length`步骤):`var avg = times.reduce(function(p,c,i){return p +( CP)/(I + 1)},0);` (11认同)
  • @furf 5年后,它看起来像在许多现代浏览器中,更优雅的"reduce()"更快(或更快).在Chrome 65中,大多数firefox reduce在该测试中表现更好. (11认同)
  • 在ES2015中,它更加优雅.`times.reduce((a,b)=>(a + b))/ times.length;` (9认同)
  • @zamnuts我和你在一起,我觉得Thor84没有评论完全没有问题 - 我很乐意从一个发现array.reduce过于复杂的地方被解雇.但是我也不会使用你的代码,因为简单的事实是它有一个除法和两个额外的加法,它永远不会像最后一个单独的一个部分那样有效 (6认同)

Mar*_*cck 122

var sum = 0;
for( var i = 0; i < elmt.length; i++ ){
    sum += parseInt( elmt[i], 10 ); //don't forget to add the base
}

var avg = sum/elmt.length;

document.write( "The sum of all the elements is: " + sum + " The average is: " + avg );
Run Code Online (Sandbox Code Playgroud)

只需遍历数组,因为您的值是字符串,所以必须先将它们转换为整数.而平均值只是值的总和除以值的数量.

  • 我要做的唯一改进是将`for(var i = 0; i <elmt.length; i ++;)`替换为`for(var i = 0,l = elmt.length; i <l; i ++) ` (13认同)
  • 注意划分0(elmt.length可能是0) (9认同)
  • @VitoGentile和DanD丑化了现代浏览器编译的性能提升代码,这不应该是最佳实践. (9认同)
  • 不要成为那个人或偏离主题,但在parseInt()中包含radix参数是一个好习惯.我的意思是'sum + = parseInt(elmt [i],10);`假设elmt [i]是基数10. [link](https://developer.mozilla.org/en-US/docs/网络/ JavaScript的/参考/ Global_Objects/parseInt函数) (4认同)
  • @BramVanroy短篇小说:不,它不会每次都设置'l'.长话:DanD的解决方案是提高性能/速度,因为每次迭代检查数组的长度比实际将长度存储在局部变量中并在每次迭代时引用它要慢. (2认同)

Abd*_*UMI 96

ES6

const average = arr => arr.reduce( ( p, c ) => p + c, 0 ) / arr.length;
    
const result = average( [ 4, 4, 5, 6, 6 ] ); // 5
    
console.log(result);
Run Code Online (Sandbox Code Playgroud)

  • 请不要扩展非代码创建的对象. (37认同)
  • 当没有长度时,这会剧烈崩溃 (4认同)
  • 改进:`Array.prototype.average = function(){var sum = 0,j = 0; for(var i = 0; i &lt;this.length,isFinite(this [i]); i ++){sum + = parseFloat(this [i]); ++ j; }返回j?sum / j:0; };` (3认同)
  • @JimmyKane 不,它会返回`NaN`。 (2认同)

Tom*_*zyk 30

使用reduce和ES6 计算平均值(平均值):

const average = list => list.reduce((prev, curr) => prev + curr) / list.length;

const list = [0, 10, 20, 30]
average(list) // 15
Run Code Online (Sandbox Code Playgroud)


Shi*_*kin 20

通常使用单线减少的平均值是这样的

elements.reduce(function(sum, a,i,ar) { sum += a;  return i==ar.length-1?(ar.length==0?0:sum/ar.length):sum},0);
Run Code Online (Sandbox Code Playgroud)

专门问问题

elements.reduce(function(sum, a,i,ar) { sum += parseFloat(a);  return i==ar.length-1?(ar.length==0?0:sum/ar.length):sum},0);
Run Code Online (Sandbox Code Playgroud)

一个有效的版本就像

elements.reduce(function(sum, a) { return sum + a },0)/(elements.length||1);
Run Code Online (Sandbox Code Playgroud)

在1分钟内了解Javascript数组减少 http://www.airpair.com/javascript/javascript-array-reduce

正如gotofritz所指出的那样,Array.reduce会跳过未定义的值.所以这是一个修复:

(function average(arr){var finalstate=arr.reduce(function(state,a) { state.sum+=a;state.count+=1; return state },{sum:0,count:0}); return finalstate.sum/finalstate.count})([2,,,6])
Run Code Online (Sandbox Code Playgroud)

  • `elements.length!= 0?elements.length:1`也可以这样写:`elements.length || 1`更短,更容易阅读. (2认同)
  • 请记住,这仅适用于没有空隙的数组 (2认同)
  • 建议:添加代码片段的未缩小(实际上只是打印精美)版本,以便人们可以阅读它们。我会自己编辑它们,但我不喜欢在这种程度上改变人们的答案。 (2认同)

chi*_*ens 17

平均最短的一个班轮:

let avg = [1,2,3].reduce((a,v,i)=>(a*i+v)/(i+1));
Run Code Online (Sandbox Code Playgroud)

总和最短的一个班轮:

let sum = [1,2,3].reduce((a,b)=>a+b);
Run Code Online (Sandbox Code Playgroud)

  • 如果将返回值切换为“a+(va)/(i+1)”,您将保留相同数量的字符,并使其在数值上更加稳定,特别是相对于所有除以“array.length”的答案 (2认同)

小智 14

让我们假设我们有一个这样的整数数组:

var values = [ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11];
Run Code Online (Sandbox Code Playgroud)

平均值通过以下公式获得

A =(1/n)Σxi (i = 1到n) ......所以:x1/n + x2/n + ... + xn/n

我们将当前值除以值的数量,并将先前的结果添加到返回的值.

reduce方法签名是

reduce(callback[,default_previous_value])
Run Code Online (Sandbox Code Playgroud)

reduce回调函数采用以下参数:

  • p:先前计算的结果
  • c:当前值(来自当前指数)
  • i:当前数组元素的索引值
  • a:当前减少的阵列

第二个reduce参数是默认值 ...(用于数组为空的情况).

所以平均reduce方法将是:

var avg = values.reduce(function(p,c,i,a){return p + (c/a.length)},0);
Run Code Online (Sandbox Code Playgroud)

如果您愿意,可以创建单独的功能

function average(p,c,i,a){return p + (c/a.length)};
function sum(p,c){return p + c)};
Run Code Online (Sandbox Code Playgroud)

然后简单地参考回调方法签名

var avg = values.reduce(average,0);
var sum= values.reduce(sum,0);
Run Code Online (Sandbox Code Playgroud)

或者直接扩充Array原型..

Array.prototype.sum = Array.prototype.sum || function (){
  return this.reduce(function(p,c){return p+c},0);
};
Run Code Online (Sandbox Code Playgroud)

每次调用reduce方法时都可以对值进行除法.

Array.prototype.avg = Array.prototype.avg || function () {
  return this.reduce(function(p,c,i,a){return p+(c/a.length)},0);
};
Run Code Online (Sandbox Code Playgroud)

或者甚至更好,使用预先定义的 Array.protoype.sum()

方法,优化过程我只调用一次除法:)

Array.prototype.avg = Array.prototype.avg || function () {
  return this.sum()/this.length; 
};
Run Code Online (Sandbox Code Playgroud)

然后在范围的任何Array对象上:

[2, 6].avg();// -> 4
[2, 6].sum();// -> 8
Run Code Online (Sandbox Code Playgroud)

注意:在我的观点中,返回NaN愿望的空数组比0更正确,并且在特定用例中非常有用.


Gen*_*wen 13

您还可以在数学部分中使用lodash,_.sum(数组)和_.mean(数组)(还有其他方便的工作人员).

_.sum([4, 2, 8, 6]);
// => 20
_.mean([4, 2, 8, 6]);
// => 5
Run Code Online (Sandbox Code Playgroud)


Joh*_*ria 6

不是最快的,但是最短且在一行中使用map()和reduce():

var average = [7,14,21].map(function(x,i,arr){return x/arr.length}).reduce(function(a,b){return a + b})
Run Code Online (Sandbox Code Playgroud)

  • @Tobiq,你的代码不是很清楚.乍一看这种类型的循环是难以理解的. (2认同)

Kei*_*ith 5

我在个人库中使用以下方法:

Array.prototype.sum = Array.prototype.sum || function() {
  return this.reduce(function(sum, a) { return sum + Number(a) }, 0);
}

Array.prototype.average = Array.prototype.average || function() {
  return this.sum() / (this.length || 1);
}
Run Code Online (Sandbox Code Playgroud)

编辑:要使用它们,只需向数组求和或平均值即可,例如:

[1,2,3].sum() // = 6
[1,2,3].average() // = 2
Run Code Online (Sandbox Code Playgroud)


Obo*_*hin 5

In ES6-ready browsers this polyfill may be helpful.

Math.sum = (...a) => Array.prototype.reduce.call(a,(a,b) => a+b)

Math.avg = (...a) => this.sum(...a)/a.length;
Run Code Online (Sandbox Code Playgroud)

You can share same call method between Math.sum,Math.avg and Math.max,such as

var maxOne = Math.max(1,2,3,4) // 4;
Run Code Online (Sandbox Code Playgroud)

you can use Math.sum as

var sumNum = Math.sum(1,2,3,4) // 10
Run Code Online (Sandbox Code Playgroud)

or if you have an array to sum up,you can use

var sumNum = Math.sum.apply(null,[1,2,3,4]) // 10
Run Code Online (Sandbox Code Playgroud)

just like

var maxOne = Math.max.apply(null,[1,2,3,4]) // 4
Run Code Online (Sandbox Code Playgroud)