1.利用assign合并多个对象,第一个参数为目标对象,后面可以有多个源对象。
首先我们需要知道的是assign实行的是浅拷贝,也就是说如果源对象的某个属性值是对象,那么assign拷贝的是它的引用。
assign是将源对象的可枚举属性复制到目标对象,如果属性名相同后面的属性会覆盖前面属性,只有一个参数assign会直接返回该参数。
如果参数不是对象,assign会先将其转为对象,再进行操作
assign可以处理数组,但数组会被视为对象
let
obj1 = {
name
:
'dk'
,
age
:
'99'
,
feature
:
'stronge'
let
obj2 = {
name
:
'tk'
,
age
:
'99'
,
feature1
:
'noStronge'
,
address
: {
city
:
'广州'
,
address
: {
city
:
'深圳'
skills
: [
'JavaScript'
,
'React'
,
'Node'
]
let
res =
Object
.
assign
(obj1, obj2);
res.
address
.
address
.
city
=
'广州'
;
console
.
log
(obj2);
console
.
log
(res);
2.利用扩展运算符
需要注意的是利用扩展运算符...合并对象 同样是进行浅拷贝
let obj1 = {
name: 'dk',
age: '99',
feature: 'stronge'
let obj2 = {
name: 'tk',
age: '99',
feature1: 'noStronge',
address: {
city: '广州',
address: {
city: '深圳'
skills: ['JavaScript', 'React', 'Node']
let res = {...obj1, ...obj2};
res.address.address.city = '杭州';
console.log(obj2);
console.log(res);
3.手写函数(浅拷贝实现)
let merger = (...opts) => {
let res = {};
let combine = (opt) => {
for(let prop in opt) {
if(opt.hasOwnProperty(prop)) {
res[prop] = opt[prop];
for (let i = 0; i < opts.length; i++) {
combine(opts[i]);
return res;
let obj1 = {
name: 'dk',
age: '99',
feature: 'stronge'
let obj2 = {
name: 'tk',
age: '99',
feature1: 'noStronge',
address: {
city: '广州',
address: {
city: '深圳'
skills: ['JavaScript', 'React', 'Node']
let res = merger(obj1, obj2);
res.address.address.city = '杭州';
console.log(res);
console.log(obj2);
上面实现的函数主要的知识点有
Object对象的hasOwnProperty方法,主要用于判断实例对象是否有该属性。
for in循环主要用于遍历对象属性。不管是自身的还是继承的属性。
既然说到for in,顺便提一下for of 与for in的区别
先说结论,for in 一般用于遍历对象属性,for of 一般用于遍历数组。
官方文档给的解释是for in 用于循环一个可枚举对象,for of用于可迭代对象,可枚举对象和可迭代对象之间的关系就是:可枚举对象视为矩形,可迭代对象视为正方形。因此,所有可迭代对象都是可枚举对象,但并非所有可枚举都是可迭代对象。它们之间的关系就和矩形和正方形之间差不多。
用object来说的话,for in遍历的是key,for of 遍历的是value,但是js中的object用for of会直接报错。
4.手写函数(实现深拷贝)
下面实现深拷贝的函数思路和浅拷贝差不多,就是多出了一个递归,如果有不了解递归的小伙伴,可以去了解一下。
let merger = (...opts) => {
let res = {};
let combine = (opt) => {
for(let prop in opt) {
if(opt.hasOwnProperty(prop)) {
if(Object.prototype.toString.call(opt[prop]) === '[object Object]') {
res[prop] = merger(res[prop], opt[prop]);
}else {
res[prop] = opt[prop];
for (let i = 0; i < opts.length; i++) {
combine(opts[i]);
return res;
let obj1 = {
name: 'dk',
age: '99',
feature: 'stronge'
let obj2 = {
name: 'tk',
age: '99',
feature1: 'noStronge',
address: {
city: '广州',
address: {
city: '深圳'
skills: ['JavaScript', 'React', 'Node']
let res = merger(obj1, obj2);
res.address.address.city = '杭州';
console.log(obj2);
console.log(res);
上面代码的知识点有
Object.prototype.toString.call() 用于判断类型,他其实是toString( )方法和call( )方法结合使用,toString( ) 方法用于返回对象类型字符串,而call( )方法就是绑定this嘛。
上面在merger中调用merger就是递归的思想,有兴趣的小伙伴可以去学学递归的思想。
5.最后介绍最后一种办法Lodash's中的merge( )方法。Lodash's是node中的库。它也是一种深拷贝的办法。
const _ = require('lodash');
let obj1 = {
name: 'dk',
age: '99',
feature: 'stronge'
let obj2 = {
name: 'tk',
age: '99',
feature1: 'noStronge',
address: {
city: '广州',
address: {
city: '深圳'
skills: ['JavaScript', 'React', 'Node']
const res = _.merge(obj1, obj2);
console.log(res);
复制代码