JavaScript数组方法--reduce、reduceRIght、reverse

  今天写的reduce是比较复杂的一个数组方法,其实在这之前我也用过reduce,可是每次用起来总感觉不那么顺手,主要还是因为不熟,对reduce本身不熟。首先reduce这个单词翻译为中文,不那么直观,再加上他的示例比较简单,导致用在复杂情况下,就有点懵逼的感觉。通过自己的理解,我们重构一次,可能更能够方便理解!

  • reduce:reduce() 方法对数组中的每个元素执行一个由您提供的reducer函数(升序执行),将其结果汇总为单个返回值。
    看到MDN给的这句解释,可能就懵了!
    什么叫reducer函数?为什么升序执行?
    我们直接看示例吧(虽然他的示例简单了点)!

    const array1 = [1, 2, 3, 4];
    const reducer = (accumulator, currentValue) => accumulator + currentValue;
    console.log("不提供初始化的值:" + array1.reduce(reducer));
    console.log("初始化值为5:" + array1.reduce(reducer, 5));
    

      
    看结果:

    似乎隐隐约约明白点什么了,但是又不那么清晰!那好,我们继续!
    语法:

    arr.reduce(callback[, initialValue])
    

      接受一个回调函数callback:执行数组中每个值的函数,包含四个参数:
      

    一个可选的初始化的值initialValue:作为第一次调用 callback函数时的第一个参数的值。 如果没有提供初始值,则将使用数组中的第一个元素。 在没有初始值的空数组上调用 reduce 将报错。

    到这里,如果还是没怎么明白的话,简单翻译一下,就是reduce方法对数组中的每个元素顺序执行一遍回调函数。用上例来说就是,将数组array1中元素在initialValue的基础上累加,如果没有提供initailValue,默认值为array1[1]。
    再看上面的两次调用:

    console.log("不提供初始化的值:" + array1.reduce(reducer));

    第一次没有初始值,那就是数组中元素求和。

    console.log("初始化值为5:" + array1.reduce(reducer, 5));  

    这一次initailValue为5,那就是所有元素求和加上5。
    再来一次稍微复杂点的示例吧!

    const persons = [{name: ‘zhang‘, age: 12}, {name: ‘leo‘, age: 32}, {name: ‘gre‘, age: 21}];

    选取persons当中年龄最大的元素!

    let person = persons.reduce(function(current, item){
          return item.age > current.age ? item : current
    })
    console.log(person)

    我们按照上面解释的reduce对照理解一下需求和代码,就是persons数组当中选取出age值最大的元素。
    而我们的person是怎么执行的呢,一个累计器current,计算到当前元素时,age最大的元素,第一次执行,没有提供初始值,那默认初始值为persons[0]。与自身比较不管是什么结果,都返回persons[0]。第二次执行,用persons[1]与persons[0]比较,返回persons[1]。再用persons[1]与persons[2]比较,依然返回persons[1]。
    似乎有点明白了。
    好,再来一个需求,计算所有元素age的和。

    let age = persons.reduce(function(current, item){
          return typeof current !== ‘number‘? (item.age+ current.age) : item.age + current
    })

    当你自己写一遍的时候,会发现总会有各种各样的问题。原因在哪呢?
    关键点:如果没有初始化值,那默认的初始化值是数组的第一个元素。看出来了吗?我们这里没有提供初始化值,所以默认初始化值是persons[0]。所以最开始的累计器是一个对象{},而我们实际上需要返回的是一个数字(所有年龄求和),所以说当结果类型与元素类型不一致,同时你又没有传递初始化值,那么就只能说自己坑自己了。最简单的方法,其实是在这里传递一个初始化的值0.

    let age = persons.reduce(function(current, item){
          return item.age + current
    },0)

    依然懵逼。。。
    好吧,算了,重构一下吧!

    function reduce (arr, fn, initialValue) {
        if (!(arr instanceof Array)) throw new Error("请确保第一个参数类型为数组")
        var accumulator = initialValue !== undefined ? initialValue : arr[0]
        var j = initialValue !== undefined ? 0 : 1
        for (var i = j; i < arr.length; i++) {
          accumulator = fn(arr[i], accumulator, i + j, arr)
        }
        return accumulator
      }

    看这一小段代码,再回头理解累计器accumulator和初始化值initialValue。对照前面的说法,再来理解reduce方法。

  • reduceRight:reduceRight() 方法接受一个函数作为累加器(accumulator)和数组的每个值(从右到左)将其减少为单个值。
    看名称,与reduce方法应该就没有特别大的区别,只不过reduce升序(从左到右),而当前这个reduceRight降序(从右到左),直接重构吧。

    function reduceRight (arr, fn, initialValue) {
        if (!(arr instanceof Array)) throw new Error("请确保第一个参数类型为数组")
        var len = arr.length, accumulator = initialValue
        if (initialValue === undefined) {
          len = arr.length - 1
          accumulator = arr[len]
        }
        while (len) {
          accumulator = fn(arr[len - 1], accumulator, len - 1)
          len--
        }
        return accumulator
      }

    其实比较方便的方法,是对照reduce的for循环,从最后一个元素向前。

  • reverse:reverse() 方法将数组中元素的位置颠倒,并返回该数组。该方法会改变原数组。
    reverse还是比较简单的,从字面理解就是相反,也就是数组变成倒序,需要注意的是会改变原数组,也比较常见,直接重构!
    function reverse (arr) {
        if (!(arr instanceof Array)) throw new Error("请确保参数类型为数组")
        var i = Math.ceil(arr.length / 2)
        for (var j = 0; j < i; j++) {
          var temp = arr[j]
          arr[j] = arr[arr.length - j - 1]
          arr[arr.length - j - 1] = temp
        }
        return arr
      }

原文地址:https://www.cnblogs.com/zhuhuoxingguang/p/10670457.html

时间: 2024-08-01 11:06:10

JavaScript数组方法--reduce、reduceRIght、reverse的相关文章

几个关于js数组方法reduce的经典片段

以下是个人在工作中收藏总结的一些关于javascript数组方法reduce的相关代码片段,后续遇到其他使用这个函数的场景,将会陆续添加,这里作为备忘. javascript数组那么多方法,为什么我要单挑reduce方法,一个原因是我对这个方法掌握不够,不能够用到随心所欲.另一个方面,我也感觉到了这个方法的庞大魅力,在许多的场景中发挥着神奇的作用. 理解reduce函数 reduce() 方法接收一个函数作为累加器(accumulator),数组中的每个值(从左到右)开始缩减,最终为一个值. a

JavaScript数组方法详解

JavaScript数组方法详解 JavaScript中数组的方法种类众多,在ES3-ES7不同版本时期都有新方法:并且数组的方法还有原型方法和从object继承的方法,这里我们只介绍数组在每个版本中原型上的方法,本文举例介绍了从ES3到ES7几乎所有的数组方法.这大概是最全的数组方法详解了.希望读者能从中有所收获. 一.各版本数组方法一览表 数组方法名 对应版本 功能 原数组是否改变 pop() ES3- 删除最后一位,并返回删除的数据 是 push() ES3- 在最后一位新增一或多个数据,

JavaScript数组方法对比(深度学习数组)

JavaScript数组方法对比 众所周知,JavaScript提供了许多对数组进行改变的方法,但是有些会对原数组进行影响,有些不会.下边就列举出来. 一.新增 影响原数组 array.push()  //向数组的末尾添加一个或更多元素,并返回新的长度. var array =[1,2,3,4,5]; array.push(6); // [1,2,3,4,5,6]; array.unshift() //向数组的开头添加一个或更多元素,并返回新的长度. var array =[1,2,3,4,5]

JavaScript数组方法总结

由于最近都在freecodecamp上刷代码,运用了很多JavaScript数组的方法,因此做了一份关于JavaScript教程的整理,具体内容如下: 一.普通方法 1.join() 将数组元素连接在一起,并以字符串形式返回参数:可选,指定元素之间的分隔符,没有参数则默认为逗号返回值:字符串对原数组的影响:无2.reverse()将数组的元素顺序变成倒序返回参数:无返回值:数组对原数组的影响:原数组被修改为倒序排列之后的数组3.sort()对数组元素进行排序并返回参数:可选,排序的方法函数,没有

JavaScript 数组方法总结

最近公司没项目.所以所幸学学JS.毕竟很多人和我一样.属于培训机构出来的.JS基础也很差. 面试的时候面试官问你 .你会JS不.你会毫不犹豫的回答会.因为你确实用过.但是真正会的或许只是以前项目中需要的方法. 鉴于这种情况 我决定把JS基础篇的东西像JAVA或.net一样在博客园阐述一到. 虽然第一次发技术贴.但是我还是看了很多帖子.我不会很不负责的复制代码 然后走人了事.以下为总结部分: <script type="text/javascript"> function 数

JavaScript数组方法大全(第二篇)

数组方法大全(第二篇) 注意:如有错误欢迎指出,如有雷同纯属巧合,本博客参考书籍JavaScript权威指南,有兴趣的小伙伴可以去翻阅一下哦 forEach()方法 遍历数组,里面可以传递一个方法 var arr = [1,2,3]; arr.forEach(function (item,index,array) { //item:表示数组中元素的每一项 //index:表示每一项所对应的索引 //array:表示原数组 }) map()方法 将调用数组的每个元素传递给指定的函数,并返回一个新的

JavaScript - 数组方法应用

数组方法应用 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">

javascript数组方法

javascript有许多数组方法,今天整理了一下: var a=[1,2,3]; a.join();//将数组中所有元素都转化为字符串并连接在一起,参数作为分隔符. a.reverse();//将数组中的元素点到顺序,返回逆序数组. a.sort();//将数组中的元素排序并返回排序后的数组. a.concat();//创建并返回一个新数组,其中返回数组包括a中元素和参数. a.slice();//方法返回制定数组的一个片段或子数组,通过下标作为参数截取. a.splice();//在数组中插

4个错误使用JavaScript数组方法的案例

译者按: 做一个有追求的工程师,代码不是随便写的! 原文: Here's how you can make better use of JavaScript arrays 译者: Fundebug 为了保证可读性,本文采用意译而非直译.另外,本文版权归原作者所有,翻译仅用于学习. 小编推荐:Fundebug专注于JavaScript.微信小程序.微信小游戏,Node.js和Java线上bug实时监控.真的是一个很好用的bug监控服务,众多大佬公司都在使用. 我保证这是一篇可以快速阅读并吸收的文章