假设有这样一个数组:

let person = [
{id: 0, name: "小明"},
{id: 1, name: "小张"},
{id: 2, name: "小李"},
{id: 3, name: "小孙"},
{id: 1, name: "小周"},
{id: 2, name: "小陈"},
]

我们想去掉数组中id重复的对象,比如同样id为2的两个对象——

{id: 2, name: "小李"}和{id: 2, name: "小陈"} (去掉任何一个都可以)

我们该如何去做呢?

事实上,对于数组对象,传统的去重方法无能为力,至于forEach()、filter()等迭代方法也不好使;真正能做到优雅去重的,是ES5新增加的一个方法——reduce()

reduce()方法接收一个回调函数作为第一个参数,回调函数又接受四个参数,分别是:

1.previousValue => 初始值或上一次回调函数叠加的值;

2. currentValue => 本次回调(循环)将要执行的值;

3. index =>“currentValue”的索引值;

4. arr => 数组本身;

reduce()方法返回的是最后一次调用回调函数的返回值;

let log = console.log.bind(console);
let arr = [1,2,3,4,5,6];
arr = arr.reduce((previousValue, currentValue) => {
return previousValue + currentValue; //返回的是最后一次调用回调函数的值,15+6;
})
log(arr); //

可以看出,上面代码的最终结果就是1+2+3+4+5+6 = 21;

此外,reduce还可以接收第二参数initialValue,用来声明回调函数(第一个参数)的previousValue的类型和初始值

let log = console.log.bind(console);
let arr = [1,2,3,4,5,6];
arr = arr.reduce((previousValue,currentValue) => {
return previousValue + currentValue;
},0) //指定cur的类型为Number并且初始值为0,当设为1时,最终打印的值为22
log(arr); //

需要注意的是,如果设置了initialValue的值,第一次执行回调函数的previousValue的值等于initialValue,此时查看当前索引(index)为0;但如果不设置initialValue的值,previousValue的值为数组的第一项,并且索引值(index)为1;也就是说,不设置初始值的话reduce()方法实际是从第二次循环开始的!

现在让我们回到文章开头的那个数组:

let log = console.log.bind(console);
let person = [
{id: 0, name: "小明"},
{id: 1, name: "小张"},
{id: 2, name: "小李"},
{id: 3, name: "小孙"},
{id: 1, name: "小周"},
{id: 2, name: "小陈"},
]; let obj = {}; person = person.reduce((cur,next) => {
obj[next.id] ? "" : obj[next.id] = true && cur.push(next);
return cur;
},[]) //设置cur默认类型为数组,并且初始值为空的数组
log(person);

打印person后,我们就可以得到去重后的数组。

当然, redecu()除了累加和去重外,功能还有很多,比如可以扁平化多维数组——

var flattened = [[0, 1], [2, 3], [4, 5]].reduce(function(a, b) {
return a.concat(b);
}, []); // [0,1,2,3,4,5]

再说句题外的,提到去重,很多人都会想到ES6的Set;不过根据我的实验,Set还是适合对基本类型的去重,如果Set中的每一项是对象的话,是不会去重的,j即使有的对象一模一样——

let arr = new Set([
{id: 0, name: "小明"},
{id: 0, name: "小明"},
{id: 0, name: "小明"},
{id: 0, name: "小明"}
]);
console.log([...arr]); //依旧是这4个对象

从给数组中的对象去重看Javascript中的reduce()的更多相关文章

  1. 【你不知道的javaScript 中卷 笔记1】javaScript中的类型与值

    一.类型与值 1.0 javaScript 七种内置类型: 空值(null) 未定义(undefined) 布尔值( boolean) 数字(number) 字符串(string) 对象(object ...

  2. IOS5中的Safari不兼容Javascript中的Date问题,做下笔录吧!奶奶的,折腾我半天!

    在做Mobile终端的Website开发中,我遇到一个很懊恼的问题. 在IOS5以上版本(不包含IOS5)中的Safari浏览器能正确解释出Javascript中的 new Date('2013-10 ...

  3. IOS5中的Safari不兼容Javascript中的Date问题

    在IOS5以上版本(不包含IOS5)中的Safari浏览器能正确解释出Javascript中的 new Date('2016-06-07') 的日期对象. 但是在IOS5版本里面的Safari解释ne ...

  4. Jquery中$(document).ready()与传统JavaScript中的window.onload方法的区别(2016/8/3)

    Jquery中$(document).ready()的作用类似于传统JavaScript中的window.onload方法,不过与window.onload方法还是有区别的. 1.执行时间       ...

  5. jquery中的$(document).ready()、JavaScript中的window.onload()以及body中的onload()、DomContentLoaded()区别

    $().ready().$(handler).$(document).ready(handler)均不是原生JS中的,都是jQuery中封装的方法.这些事件在当页面的dom节点加载完毕后就执行,无需等 ...

  6. 小姐姐手把手教你JS数组中的对象去重

    有时候数据库中的数据重复的,我们另一个需求需要数据的唯一性 那么这时候就用到这个方法了  我还是以截图的方式发粗来  不然太丑了 见谅 console.log(map)打印出来的结果已经帮我们把需要的 ...

  7. java list中的对象去重原理

    /******************************************************************************* * * Copyright (c) W ...

  8. JavaScript中String对象处理HTML标记中文本的方法

    big():创建一个<big></big>标记,将这个字符串的字体变大blink():创建一个<blink></blink>标记,使字符串具有闪烁效果b ...

  9. 图说js中的this——深入理解javascript中this指针

    没搞错吧!js写了那么多年,this还是会搞错!没搞错,javascript就是回搞错! ………… 文章来源自——周陆军的个人网站:http://zhoulujun.cn/zhoulujun/html ...

随机推荐

  1. setTimeout,setInterval你不知道的事

    javascript线程解释(setTimeout,setInterval你不知道的事) 标签: javascript引擎任务浏览器functionxmlhttprequest 2011-11-21 ...

  2. 个人作业-2 必应词典安卓APP分析

    产品: 必应词典 安卓版 第一部分:调研,评测 1.对于这款app的第一印象就是界面不是很美观,页面排版十分混乱,有些功能比较鸡肋,功能也不是很丰富,不过这款app的ui设计相对简洁,让人容易上手,对 ...

  3. sudoku--设想

    在查阅了一些资料和自己动手写一写后,找到一种可行的解法. 第一步 首先将9x9的数独方格分成九份3x3的九宫格,如下图 B1 B2 B3 B4 B5 B6 B7 B8 B9 而后在左上角的B1上随机生 ...

  4. 201521123008《Java程序设计》第七周实验总结

    1.本周学习总结 以你喜欢的方式(思维导图或其他)归纳总结集合相关内容. 2. 书面作业 1.ArrayList代码分析 1.1 解释ArrayList的contains源代码 public bool ...

  5. 201521123015 《Java程序设计》第2周学习总结

    1.本章学习总结 (1)学习了枚举,数组等方法 (2)通过实验内容的讲解,解决了一些问题 (3)进一步运用和了解码云 书面作业 1.使用Eclipse关联jdk源代码,并查看String对象的源代码( ...

  6. 201521123072《java程序设计》第十周学习总结

    201521123072<java程序设计>第十周学习总结 1. 本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结异常与多线程相关内容. 2. 书面作业 本次PTA作业题集异 ...

  7. 201521123067 《Java程序设计》第14周学习总结

    201521123067 <Java程序设计>第14周学习总结 1. 本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结多数据库相关内容. 2. 书面作业 Q1. MySQL数 ...

  8. 201521123060 《Java程序设计》第10周学习总结

    1.本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结异常与多线程相关内容. 异常: 1.不要乱用异常: 2.异常发生时:确定异常类型,异常位置: 3.尽量使用已有的异常类. 多线程: 2 ...

  9. OJ题

    题目:在字符串中找出连续最长的数字串 #include <stdlib.h> #include <string.h> #include <iostream> #in ...

  10. Python学习笔记008_类_对象_继承_组合_类相关的BIF

    # 对象 = 属性 + 方法>>> # Python中的类名约定以大写字母开始>>> # tt = Turtle() 这就是创建类实例的方法,其它语言用new ,它 ...