eslint报错:

  Use an object spread instead of `Object.assign` eg: `{ ...foo }`.(prefer-object-spread)

即:

  禁止使用以对象字面量作为第一个参数的 Object.assign,优先使用对象扩展。

示例:(注意:对象字面量)

Object.assign({}, foo)

改为:

{ ...foo }

思考一下:
Object.assign常用来浅拷贝,那扩展符赋值的对象是重新开辟的堆内存还是指向的扩展对象的堆内存?

    const a = { a: 'a' };
const b = { ...a };
console.log('b=', b); // b= {a: "a"}
a.a = 'c';
console.log('b变了吗', b); // b变了吗 {a: "a"}

  

  答案很明显,我想浅拷贝一个a, 扩展运算符和Object.assign都能浅拷贝对象。

  那数组会怎样?

  

    const a = ['a', 'b'];
const b = [...a];
console.log('b=', b); // b= ["a", "b"]
a[1] = 'c';
console.log('b变了吗', b); // b变了吗 ["a", "b"]

  很好,数组也能放心的浅拷贝;

  

  等等。。。

  

  如果是数组对象呢?

    const a = [{ a: 'a' }];
const b = [...a];
console.log('b=', JSON.stringify(b)); // b= [{"a":"a"}]
a[0].a = 'c';
console.log('b变了吗', JSON.stringify(b)); // b变了吗 [{"a":"c"}]

  变了,结果说明展开符只对数组里面的对象进行了展开,对象里面的属性还是指向的原来的内存地址,所以深拷贝行不通,目前来看和Object.assign的浅拷贝作用一样。

那...等等,

  

  Object.assign还有合并的作用,再来试试扩展符合并。

  

  

    const a = { a1: 'a1', a2: 'a2' };
const b = { b1: 'b1', a2: 'b2' };
const c = Object.assign({}, a, b);
const d = { ...a, ...b };
const e = { ...b, ...a };
console.log('c', c); // c {a1: "a1", a2: "b2", b1: "b1"}
console.log('d', d); // d {a1: "a1", a2: "b2", b1: "b1"}
console.log('e', e); // e {b1: "b1", a2: "a2", a1: "a1"}

   结果一样,Object.assign将b和a的属性合并到空对象里,相同属性会覆盖合并取后面的值,扩展符直接合并两个对象的属性,合并关系都是后面的覆盖前面的值。

   那么,合并数组呢?

    const a = ['a', 'b'];
const b = ['a', 'c'];
const c = Object.assign([], a, b);
const d = [...a, ...b];
console.log('c', c); // c ["a", "c"]
console.log('d', d); // d ["a", "b", "a", "c"]

   发生了什么?

   Object.assign处理数组时,会把数组视为对象,然后按顺序覆盖前面的值,所以b中的'a'覆盖了a中的'a', b中的'c'覆盖了a中的'b',而扩展符和concat方法一样合并数组。

   合并数组时,Object.assign和扩展符作用不一样了。

   

   那么,复杂数组呢?

    const a = [{ x: 'x', y: 'y' }];
const b = [{ z: 'z', y: 'm' }];
const c = Object.assign([], a, b);
const d = [...a, ...b];
console.log('c', JSON.stringify(c)); // c [{"z":"z","y":"m"}]
console.log('d', JSON.stringify(d)); // d [{"x":"x","y":"y"},{"z":"z","y":"m"}]
b[0].z = 'n';
console.log('c', JSON.stringify(c)); // c [{"z":"n","y":"m"}]
console.log('d', JSON.stringify(d)); // d [{"x":"x","y":"y"},{"z":"n","y":"m"}]

  

  Object.assign毫无悬念的后面的覆盖前面了(将数组看做对象时,属性就是下标),引用类型指向的还是原来的内存地址。

  

最后:

  

  虽然说Object.assign和...扩展符很多时候能混用,但对数组进行操作的时候一定要小心两者的区别,不然合并覆盖变成合并拼接,所以请牢记使用以对象字面量作为第一个参数的 Object.assign,优先使用对象扩展。

 

 


prefer-object-spread的更多相关文章

  1. [Python] Object spread operator in Python

    In JS, we have object spread opreator: const x = { a: '1', b: '2' } const y = { c: '3', d: '4' } con ...

  2. [Python] List & Object spread in Python

    def myfunc(x, y, z): print(x, y, z) tuple_vec = (, , ) dict_vec = {, , } >>> myfunc(*tuple_ ...

  3. js spread object

    What’s is the benefit / drawback of these two alternatives? Using object spread options = {...option ...

  4. ES6之Spread Operater拷贝对象

    译者按: 对象拷贝和合并使用展开运算符(Spread Operator)很方便! 原文: Master Javascript’s New, Cutting-Edge Object Spread Ope ...

  5. React——教程 && 零基础入门 && 从实践中学习(待续)

    Tutorial: Intro to React This tutorial doesn’t assume any existing React knowledge. Tip This tutoria ...

  6. vue.js组件化开发实践

    前言 公司目前制作一个H5活动,特别是有一定统一结构的活动,都要码一个重复的轮子.后来接到一个基于模板的活动设计系统的需求,便有了下面的内容.借油开车. 组件化 需求一到,接就是怎么实现,技术选型自然 ...

  7. npm-bluebird使用

    API 注意 时刻注意return; 使用Promise.promisify简化对test(val, function(err, result){})的处理; 尽量避免使用deferred objec ...

  8. vuex 笔记

    Vuex 笔记 一个简单的状态管理 单一数据源: const sourceOfTruth = {} const vmA = new Vue({ data: sourceOfTruth }) const ...

  9. Javascript.ReactNative-2-javascript-syntax-in-react-native

    JavaScript Syntax in React Native Contents: Arrow Function Let+Const Default + Rest + Spread Destruc ...

  10. groovy-运算符

    算术和条件运算符 Groovy支”!”操作符,例如: 1 def expression = false 2 assert !expression 基于集合的运算符: Spread Operator ( ...

随机推荐

  1. 新手学习FFmpeg - 调用API完成两个视频的任意合并

    本次尝试在视频A中的任意位置插入视频B. 在上一篇中,我们通过调整PTS可以实现视频的加减速.这只是对同一个视频的调转,本次我们尝试对多个视频进行合并处理. Concat如何运行 ffmpeg提供了一 ...

  2. Wordpress对接小程序配置过程

    最近发现一个很棒的开源项目-WordPress版微信小程序  https://github.com/iamxjb/winxin-app-watch-life.net,详细看了下介绍非常棒,不仅支持的功 ...

  3. Spring 事务注解@Transactional

    事务管理一般有编程式和声明式两种,编程式是直接在代码中进行编写事物处理过程,而声名式则是通过注解方式或者是在xml文件中进行配置,相对编程式很方便. 而注解方式通过@Transactional 是常见 ...

  4. markdown常用语法使用笔记

    markdown是当下比较流行的一种编辑标记语言,很多系统都支持markdown语法来编辑文件内容,像gitbook之类的,一下是一些学习笔记. 1.开头用#的数量表示1-6阶的标题,结尾可以以任意数 ...

  5. centos7 远程连接其他服务器mysql

    在本地远程连接 在终端输入: mysql -h 服务器ip地址 -P 端口 -u 用户名 -p 然后输入密码即可.

  6. 正睿国庆DAY2动态规划专题

    正睿国庆DAY2动态规划专题 排列-例题 1~n 的排列个数,每个数要么比旁边两个大,要么比旁边两个小 \(f[i][j]\) 填了前i个数,未填的数有\(j\)个比第\(i\)个小,是波峰 \(g[ ...

  7. Kubernetes 系列(四):使用Traefik访问.net core api

    一. 准备 本篇的要求是在前三篇的基础上已经搭建好的本地k8s以及部署了Traefik,我们将会使用Traefik Ingress来访问.net core api,比较简单,做个记录,如果还没有搭建k ...

  8. 防御 DDoS 的终极奥义——又拍云 SCDN

    现如今不论是年轻的 80.90 后,还是 70.60 后,都在享受互联网带来的舒适和便利.在家就可以"逛商场",完全不受时间的限制:在线支付既方便又安全:业余娱乐项目多种多样,打农 ...

  9. 详解http报文(2)-web容器是如何解析http报文的

    摘要 在详解http报文一文中,详细介绍了http报文的文本结构.那么作为服务端,web容器是如何解析http报文的呢?本文以jetty和undertow容器为例,来解析web容器是如何处理http报 ...

  10. Cocos Creator 3D 打砖块图文教程(一)

    在线体验链接: http://example.creator-star.cn/block3d/ 上面图中是打砖块游戏的主要 3D 节点元素,Shawn 这两天在学习 Unity 与 Creator3D ...