day225-展开运算符 vs Object.assign()

要点

  1. 展开运算符
  2. Object.assign()
  3. 以上两者的异同

展开运算符

Object Spread 只是用已存在的对象的properties创建了一个新的普通对象 具体可见tc39-proposal-object-rest-spread

  1. 构造字面量数组
let arr1 = [0, 1, 2] let arr2 = [3, 4, 5]
let mergeArr = [...arr1, ...arr2]
  1. 构造字面量对象
let obj1 = { foo: 'bar', x: 1 }
let obj2 = { foo: 'baz', y: 2 }
let mergeObj = { foo: 'baz', x: 1, y: 2 }

let mergeObj = { ...obj1, ...obj2 }
  1. 函数调用时使用展开语法
// old:
function myFn (x, y, z) {}
let args = [0, 1, 2]
myFn.apply(null, args)
// new:
function myFn (x, y, z) {}
let args = [0, 1, 2]
myFn(...args)

Object.assign()

  1. 合并对象
  2. 复制一个对象
  3. 拷贝 symbol 类型的属性, 但是不可拷贝继承属性和不可枚举属性

以上两者异同

Object.assign()会触发ES6的setters。

如果喜欢用immutable技术,对象展开符操作更加合适。

用Object.assign(),第一个参数必须是{}。

class MyClass {
set val (v) {
console.log('Setter called', v)
return v
}
}
const obj = new MyClass()
Object.assign(obj, { val: 3 }) // Setter called 3

两者都不会复制继承属性或class信息,但是可以拷贝ES6 symbols

class BaseClass {
foo() {return 1}
}
class MyClass extends BaseClass {
bar() {return 2}
}
const obj = new MyClass()
obj.baz = function() {return 3}
obj[Symbol.for('test')] = 4

const clone = { ...obj }

console.log(clone) // { baz: [Function], [Symbol(test)]: 4 }
console.log(clone.constructor.name)
console.log(clone instanceof MyClass)

参考

http://www.ecma-international.org/ecma-262/6.0/#sec-performpromisethen

https://thecodebarbarian.com/object-assign-vs-object-spread.html

https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Operators/Spread_syntax

https://github.com/tc39/proposal-object-rest-spread

文章作者: lmislm
文章链接: http://lmislm.com/2019/08/27/2019-08-27/
版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 LMISLMのBlog