什么是reduce方法?
先来看一下用用法:
var arr = [1, 2, 3, 4] var sum = (a, b) => a + b arr.reduce(sum, 0) // 10
由上面代码可以看出,reduce对数组arr的每一个成员执行了sum函数。sum的参数a是累积变量,参数b是当前的数组成员。每次执行时,b会回到a,最后输出a。
累积变量必须有一个初始值,上例是reduce函数的第二个参数0,如果省略该参数,那么初始值默认是数组的第一个成员。
var arr = [1, 2, 3, 4] var sum = function(a, b) { console.log(a, b); return a + b } arr.reduce(sum) // => 10 // 1 2 // 3 3 // 6 4
reduce省略了初始值,通过sum函数里面的打印语句,可以看到累积变量每一次的变化。reduce方法提供了一种遍历手段,对数组所有成员进行‘累积’处理。
既然是遍历,那它跟 for 、 while有什么不同呢?
for :
var arr = [1, 2, 3, 4] Array.prototype.sum = function () { var sumResult = 0; for (var i = 0; i < this.length; i++) { sumResult += parseInt(this[i]); } return sumResult; } arr.sum(); // 10
while
var arr = [1, 2, 3, 4] Array.prototype.sum = function() { var sumResult = 0; var i = this.length; while (i--) { sumResult += parseInt(this[i]); } return sumResult; } arr.sum() // 10
以上代码都能实现reduce的功能,那为何还要搞这玩意呢?
一般来说类似的方法比较都会是性能方面的比较,来看看各自的耗时
var arr = [1, 2, 3, 4] console.time('forLoop'); Array.prototype.forLoop = function() { for (var i = 0; i < 10000; i++) { var sumResult = 0; for (var j = 0; j < this.length; j++) { sumResult += parseInt(this[j]); } return sumResult; } arr.forLoop(); console.log('最终的值:' + arr.forLoop()) // 10 console.timeEnd('forLoop')
var arr = [1, 2, 3, 4]
console.time('whileLoop') Array.prototype.whileLoop = function() { var _this = this for(var i = 0; i < 10000; i++) { var sumResult = 0; var len = _this.length; while(len--) { sumResult += parseInt(_this[len]); } } return sumResult; } arr.whileLoop() console.log('最终的值:' + arr.whileLoop()) console.timeEnd('whileLoop')
经多次运行测试发现 10000次运行使用for循环 和while的时间大致相当,大概需要 4 - 7ms 不等!
那reduce呢?
var arr = [1, 2, 3, 4] console.time('reduce') Array.prototype.reduceSum = function() { for (var i = 0; i < 10000; i++) { return this.reduce(function(preValue, curValue) { return preValue + curValue; }); } } arr.reduceSum(); console.log('最终的值:' + arr.reduceSum()) // 10 console.timeEnd('reduce')
可见,时间大概在1-3ms之间,耗时情况一目了然!
reduceRight()方法
reduceRight() 方法的功能和reduce()功能是一样的,不同的是reduceRight() 从数组的末尾向前将数组中的数组项做累加。
reduceRight() 首次调用回调函数callbackfn 时,preValue 和 curValue 可以是两个值之一。如果调用reduceRight()时提供了第二个参数,则preValue等于该参数,curValue等于数组中的最后一个值。如果没有提供,则preValue等于数组最后一个值,curValue等于数组中倒数第二个值。
var arr = [0, 1, 2, 3, 4]; arr.reduceRight(function(preValue, curValue, index, array) { console.log(preValue, curValue) return preValue + curValue; }); // 10 // 4 3 // 7 2 // 9 1 // 10 0 arr.reduceRight(function(preValue, curValue, index, array) { console.log(preValue, curValue) return preValue + curValue; }, 5) // 15 // 5 4 // 9 3 // 12 2 // 14 1 // 15 0
相关文章: https://www.w3cplus.com/javascript/array-part-8.html 、 http://www.ruanyifeng.com/blog/2017/03/reduce_transduce.html