javascript数组reduce的使用

322 阅读3分钟

reduce() 方法对数组中的每个元素执行一个由您提供的reducer函数(升序执行),将其结果汇总为单个返回值。其能做的功能很多,通过回调函数实现。 reduce参数

  • 第一个参数:回调函数,其有四个参数(累加器accumulator,当前值,当前索引,原数组),后两个参数可选。
function(acc,current,index,arr)=>{
    return acc+cur;
}
  • 第二个参数:是回调函数的第一个参数累加器的初始值

注意:不给初始值,那么初始值就是原数组的第一个元素,计算从第二个元素开始。给了初始值就是从第一个元素开始。

使用场景

累加器

  • 为存储数值的数值进行累加求和
let result=[1,2,3,4].reduce((acc,cur)=>{
    return acc+cur;//acc为累加器(初始值为数组第一个元素),cur为当前元素
})
console.log(result);//输出10
//因为没初始值,所以从数组第二个元素开始计算,所以处理上面数组,回调函数共运行了3次
复制代码
  • 累加求和时给初始值
let result=[1,2,3,4].reduce((acc,cur,index,o)=>{
    return acc+cur;
},10)
console.log(result);//输出20
//因为有初始值,所以从数组第一个元素开始计算,所以处理上面数组,回调函数共运行了4次

求数组中最大的元素

const max = function (list) {
    return list.reduce(function (x, y) {
        //根据reduce方法获得数组中最大的元素
        return x > y ? x : y
    });
}

数组去重

问题描述:数组去重,顾名思义就是,把数组里的重复数值去除,使其多个相同的数值变为一个,最后使数组里不含有重复数值。

例子:有个数组:[1,2,3,4,4,5,5,5,6,7],数组去重后就变为[1,2,3,4,5,6,7]。

reduce+includes/ resuce+indexOf

var unique = function (list) {
    return list.reduce((acc, current) => {
        if (!acc.includes(current)) {
            acc.push(current);
        }
        return acc;
    }, []);
};

filter+indexOf

var unique = function (list) {
    return list.filter((current, index, arr)=>{
        return arr.indexOf(current) === index;
    });
};

扩展运算符...+Set

var unique = function (list) {
    var set = new Set(list);
    return [...set];
};

{}+Object.keys()

var unique = function (list) {
    var map = {};
    list.forEach((value, index)=>{
        if(!map[value]) {
            map[value] = true;
        }
    });
    return Object.keys(map);
};

与这个相似的实现还有

  • 新数组+include
  • 新数组+indexOf
  • Map + [...map.keys()]

对象按属性分类

const bills=[{type:'transfer',momey:233},             {type:'study',momey:341},             {type:'shop',momey:821},             {type:'transfer',money:821},             {type:'study',momey:821}            ]
let result=bills.reduce((acc,cur)=>{
    if(!acc[cur.type]){// 遇到不存在的类型,就新建一个空数组来装
        acc[cur.type]=[];//二维数组
    }
    acc[cur.type].push(cur)
    return acc;
},[])//为累加器设置初始值为空数组,作为分类用的容器
console.log(result);
//输出
[  transfer: [{ type: 'transfer', momey: 233 },{ type: 'transfer', money: 821}],
  study: [ { type: 'study', momey: 341 }, { type: 'study', momey: 821 } ],
  shop: [ { type: 'shop', momey: 821 } ]
]

请使用原生 JavaScript 实现一个方法,判断 html 中出现次数最多的标签,并统计这个次数。

步骤:

  1. 获取所有标签:document.querySelector(*):获得含有所有标签的NodeList数组。
  2. 将NodeList转化为list [...NodeList];
  3. 使用reduce将nodelist转化为对象,以标签名为属性名,标签数量为属性值的对象。
  4. 通过Object.entries()将元素枚举成数组 例如:Object.entires({a:1,b:2,c:3})会得到[ [ 'a', 1 ], [ 'b', 2 ], [ 'c', 3 ] ]
  5. 使用reduce将数组最大值返回
window.onload=function(){
    function getFrequentTag(){
        //得到nodeList
        const tagMap=[...document.querySelectorAll('*')].map(x=>x.tagName).reduce((acc,tag)=>{
            acc[tag]=acc[tag]?acc[tag]+1:1;
            //数组存在该元素,就值+1,否则创建元素,设置值为1
            return acc;//得到以tag名为属性名,数量为属性值的对象
        },{})//初始值为对象
        return Object.keys(tagMap).reduce((acc, current) => {
            return tagMap[acc] > tagMap[current] ? acc : current;
        });
    }
    console.log(getFrequentTag());
}

升级版,获得出现第x次的标签

var maxCount = function (list, x) {
    const map=[...document.querySelectorAll('*')].map(x=>x.tagName).reduce((acc,tag)=>{
            acc[tag]=acc[tag]?acc[tag]+1:1;]
            return acc;]
        },{});
    var list = Object.keys(map).sort((a, b)=>{
        return map[b]-map[a]
    })
    return x<0? list[list.length+x]: list[x];
};