JavaScript - reduce()函数的示例 JavaScript - reduce()函数的示例

11
我正在看这个使用reduce()函数的例子。
function add(runningTotal, currentValue) {
   return runningTotal + currentValue;
}

var nums = [1,2,3,4,5,6,7,8,9,10];
var sum = nums.reduce(add);
print(sum); // displays 55

你能给我展示一些使用reduce()的其他例子吗?我不太确定它的工作原理。

2
你提供的例子有什么问题? - Sampson
1
看一下这个。https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Array/Reduce - Shyju
Array.prototype.reduce 的实际实现可能会提供更多信息:https://github.com/v8/v8/blob/70c4bf13315145be89e9f8b7f4313fab2442dcda/src/js/array.js#L1480 - zerkms
我对reduce()函数的作用感到困惑。add()函数也让我感到困惑。add函数需要两个参数,但当传递给reduce函数时,add函数没有参数。您能否解释一下它们是如何工作的? - Wasteland
这是因为它是对传递给 nums.reduce() 的函数的引用。然后,Array.prototype.reduce 实现会将该函数引用并在每个元素上调用它(并传递4个参数以确保精度)。 - zerkms
显示剩余2条评论
4个回答

11

reduce函数的作用是接收一个initialValue,一个带有2个必要参数(还可以有更多)的function以及一个值的list。如果没有提供initialValue,就默认使用列表中的第一个元素。这个函数通常会对previousValue进行操作,它被用作累加器,并且还会操作nextValue

例如,假设你有一个值的列表:[1, 2, 3, 4, 5],并且这个函数的作用是将两个参数相加,同时提供0作为initialValue

第一步:

0 + 1 = 1
    2
    3
    4
    5

第二步:

1 + 2 = 3
    3
    4
    5

第三步:

3 + 3 = 6
    4
    5

第四步:

6 + 4 = 10
    5

第五步:

10 + 5 = 15 //Final value

正如你所看到的,输入从list变成了一个单一的值,因此被称为reduce。在你的例子中,没有提供initialValue(第二个参数),所以它就像是从第二步开始。


我觉得现在有意义了。这真的与以下代码没有太大区别:function myAdd(arr) { var sum = 0; for (var i = 0; i < arr.length; ++i) { sum += arr[i]; } console.log("for: " + sum); }myAdd(nums); - Wasteland
正确,这将产生相同的结果,但请注意reduce更通用。在我的例子中,它对每个步骤执行x + y,这是提供的函数。实际上,它在每个步骤上执行f(x, y)f可以远不止于仅仅累加值。 - MinusFour

4
你可以为 reduce 设置第二个参数。

function add(runningTotal, currentValue) {
   return runningTotal + currentValue;
}
var someInitValue = 10
var nums = [1,2,3,4,5,6,7,8,9,10];
var sum = nums.reduce(add, someInitValue);
console.log(sum); // displays 65


而且更进一步 - 始终指定初始值是有意义的。 - zerkms

4

reduce() 通过迭代数组并调用一个归约函数(这个函数是传递给 reduce() 的第一个参数)来工作。该函数有四个参数:

  • previousValue,它类似于“运行总和”。除非你提供一个种子值作为第二个参数传递给reduce(),否则它最初为 undefined。
  • currentValue,它是数组中的对象。
  • index,当前值在数组中的索引。
  • array,数组本身。

当你的归约函数被调用时,其返回值成为下一次调用归约函数时的新的 previousValue 参数。这就是魔力所在。在归约函数被调用并给出数组中的最后一个对象之后,它的返回值将是reduce()的返回值。

老实说,你将看到的许多例子(比如使用reduce()来累加一堆整数)都可以用for()循环轻松完成。但它的真正价值在于你正在进行函数式编程


3
你可以使用reduce来生成某种流密码。
var plaintext = "thisisaplaintext";
var chars = plaintext.split('');
var result = '';
function encrypt(runningTotal, currentValue){
    var newVal = ((runningTotal + (""+runningTotal).charCodeAt()-32) % 94)+32
    result  = result + String.fromCharCode(newVal)
    return newVal;
}
chars.reduce(encrypt, 15 /*any arbitrary starting value*/);
console.log(result);

基本上,任何可以通过独立计算组合或需要一些滚动总数的东西都可以实现。这并不是你不能用for循环做到的,但它看起来更加简洁。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接