JavaScript中的深拷贝和浅拷贝

2023-06-30 0 696

甚么是深复本/浅复本

浅复本是建立两个新第一类,那个第一类具备原初第一类特性值。假如特性是基本上类别不然,复本的是基本上类别。假如特性是提及类别,复本的是提及门牌号,发生改变了当中两个第一类,就会负面影响到除此之外两个第一类。深复本是将两个第一类从缓存中完备复本了这份,从堆缓存中开拓了两个捷伊地区放置新第一类,修正后不能负面影响原本的第一类。

表达式、深复本、浅复本的差别

第一类字符串表达式给两个捷伊表达式时,只不过是赋的缓存门牌号,而并非第一类中的数据。因此修正两个将负面影响除此之外两个。var person1 = { name: 张三, age: 20, list: [1, 2, 3] } let arr = [4,5,6] var person2 = person1; person2.age = 22; person2.list = arr; person2.list[0] = 张三; console.log(person1); // {name: “张三”, age: 22, list:[“张三”, 2, 3]} console.log(person2); // {name: “张三”, age: 22, list:[“张三”, 2, 3]} console.log(arr); // [“张三”, 5, 6]浅复本是重新在堆中建立缓存,复本的基础类别互不负面影响,但是复本的提及类别共享同两个缓存门牌号,会互相负面影响。var person = { name: 张三, age: 20, list: [1, 2, 3] } function shallowCopy(object) { let temp = {}; for (const key in object) { if (Object.hasOwnProperty.call(object, key)) { temp[key] = object[key]; } } return temp; } var shallowPerson = shallowCopy(person) console.log(shallowPerson); // {name: “张三”, age: 20, list: [1, 2, 3]} shallowPerson.name = 李四; shallowPerson.list[0] = hello; console.log(person); // {name: “张三”, age: 20, list: [hello, 2, 3]} console.log(shallowPerson); // {name: “李四”, age: 20, list: [hello, 2, 3]}深复本是从堆缓存中从新建立两个地区来放置新第一类,并对第一类中的子第一类进行递归复本,互不负面影响。var person = { name: 张三, age: 20, list: [1, 2, 3] } function deepCopy(object){ let temp = Array.isArray(object) ? [] : {}; for (let key in object) { temp[key] = typeof object[key] === object ? deepCopy(object[key]) : object[key] } return temp; } var shallowPerson = deepCopy(person) console.log(shallowPerson); // {name: “张三”, age: 20, list: [1, 2, 3]} shallowPerson.name = 李四; shallowPerson.list[0] = hello; console.log(person); // {name: “张三”, age: 20, list: [1, 2, 3]} console.log(shallowPerson); // {name: “李四”, age: 20, list: [hello, 2, 3]}

浅复本的实现方式

ES6展开运算符 …

var person = { name: 张三, age: 20, list: [1, 2, 3], say:function(){console.log(hello);}, check:new RegExp(“e”) } var user = { …person} user.name = 李四 console.log(user.name); // 李四 console.log(person.name);// 张三

Object.assign()

var person = { name: 张三, age: 20, list: [1, 2, 3] } var user = Object.assign({},person) console.log(user); // // {name: “张三”, age: 20, list: [1, 2, 3]}

lodash clone

var objects = [{ a: 1 }, { b: 2 }]; varshallow = _.clone(objects);console.log(shallow[0] === objects[0]); // => true

Array concat

Array 的 concat方法不发生改变原字符串,返回两个浅复制原字符串的元素的新字符串。假如元素是提及类别,就会复本那个提及的缓存门牌号到新字符串内。两个元素提及门牌号共享,因此假如发生发生改变将负面影响除此之外两个。假如元素是基本上类别不然就会遵循浅复本的机制

vararray = [1,[2,3,4],[5,6],{name:张三}] let array_concat = array.concat() console.log(array_concat); // [1,2,3,[4,5,6],{name:张三}] array_concat[1][0] = apple console.log(array_concat[1]); // [“apple”, 3, 4] console.log(array[1]); // [“apple”, 3, 4] array_concat[2] = [apple,mac,xiaomi] // 这里之因此不一样,是因为发生改变了提及门牌号 console.log(array_concat[2]); // [“apple”, “mac”, “xiaomi”] console.log(array[2]); // [5,6] array_concat[3].name =王五; console.log(array_concat[3].name); // 王五 console.log(array[3].name); // 王五

遍历复制

function shallowCopy(object) { let temp = {}; for (const key in object) { if (Object.hasOwnProperty.call(object, key)) { temp[key] =object[key]; } } return temp; }

深复本的实现方式

JSON.parse/JSON.stringify

可以满足基本上的使用,但是对于正则表达式类别、函数类别等无法进行深复本。

var person = { name: 张三, age: 20, list: [1, 2, 3], say:function(){console.log(hello);}, check:new RegExp(“e”) } var user = JSON.parse(JSON.stringify(person)); user.name = 李四; console.log(user.name);// 李四 console.log(person.name); // 张三 user.list[0] = apple console.log(user.list); // [“apple”, 2, 3] console.log(person.list); // [1, 2, 3] console.log(user.say); // undefined console.log(user.check); // {}

lodash cloneDeep

var objects = [{ a: 1 }, { b: 2 }]; var deep = _.cloneDeep(objects); console.log(deep[0] === objects[0]); // => false

递归遍历

var person = { name: 张三, age: 20, list: [1, 2, 3], say: function () { console.log(hello); },check: new RegExp(“e”) } function cloneDeep(object, hash = new WeakMap()) { if (!isObject(object)) return object; if(object instanceof Date) return new Date(object) if(object instanceof RegExp) return new RegExp(object)if (hash.has(object)) return hash.get(object) let target = Array.isArray(object) ? [] : {}; hash.set(object, target);for (const key in object) { if (Object.hasOwnProperty.call(object, key)) { if (typeofobject[key] ===object) { target[key] = cloneDeep(object[key], hash) } else{ target[key] = object[key]; } } }return target; } function isObject(object) { return typeof object === object&& object !=null; } var user = cloneDeep(person); user.name = 李四; console.log(user.name); // 李四 console.log(person.name); // 张三 user.list[0] = apple console.log(user.list); // [“apple”, 2, 3] console.log(person.list);// [1, 2, 3] console.log(user.say); // undefined console.log(user.check); // {}

相关文章

发表评论
暂无评论
官方客服团队

为您解决烦忧 - 24小时在线 专业服务