JavaScript 深浅拷贝

JavaScript有五种基本数据类型(Undefined, null, Boolean, String, Number),还有一种复杂的数据类型,就是对象。

Undefined 其实是已声明但没有赋值的变量的输出结果,null其实就是一个不存在的对象的结果

  • 对于简单的数据类型
    它们值在占据了内存中固定大小的空间,并被保存在栈内存中。 当一个变量向另一个变量复制基本类型的值时,会创建这个值的副本,还有就是不能给基本类型的值添加属性。


    1

    2

    3

    4


    var a = 1;

    var b = a;

    a.attr = ‘long‘;

    console.log(a.attr) //undefined

    上边代码中a就是简单数据类型(number),b就是a的副本,它们两者都占有不同位置,但相等的内存空间。

  • 对于复杂的数据类型
    复杂的数据类型即引用类型,它的值是对象,保存在堆内存中,包含引用类型值的变量实际上包含的并不是对象本身,而是一个指向该对象的指针。从一个变量向另一个变量复制引用类型的值,复制的其实是指针,因此两个变量最终都指向同一个对象。

    1

    2

    3

    4

    5

    6

    7

    8


    var obj = {

    name: ‘long‘,

    age: 0

    };

    var obj2 = obj;

    obj2.c = 5;

    console.log(obj); //Oject {name: ‘long‘, age: 0, c: 5}

    console.log(obj2); //Oject {name: ‘long‘, age: 0, c: 5}

我们可以看到obj赋值给obj2后,当我们更改其中一个对象的属性值,两个对象都发生了改变,究其原因是因为obj和obj2这两个变量都指向同一个指针,赋值是复制了指针,所以当我们改变其中一个值,就会影响另一个变量的值。

浅拷贝

其实上边的代码就是浅拷贝,有时候我们只是想备份数组,但是只是简单让它赋给一个变量,改变其中一个,另外一个就紧跟着改变,但很多时候这不是我们想要的。


1

2

3

4

5

6

7

8


var obj = {

name:‘wsscat‘,

age:0

}

var obj2 = obj;

obj2[‘c‘] = 5;

console.log(obj);//Object {name: "wsscat", age: 0, c: 5}

console.log(obj2);////Object {name: "wsscat", age: 0, c: 5}

深拷贝

数组

对于数组我们可以使用slice()和concat()方法来解决上面的问题。

  • slice


    1

    2

    3

    4

    5


    var arr = [‘ge‘, ‘yu‘, ‘long‘];

    var arrCopy = arr.slice(0);

    arrCopy[0] = ‘gai‘;

    console.log(arr) // [‘ge‘, ‘yu‘, ‘long‘]

    console.log(arrCopy) // [‘gai‘, ‘yu‘, ‘long‘]

  • concat

    1

    2

    3

    4


    var arr = [‘ge‘, ‘yu‘, ‘long‘];

    var arrCopy = arr.concat();

    arrCopy[0] = ‘gai‘;

    //console跟上边一样

对象

对象我们可以定义一个新的对象并遍历新的属性去实现深拷贝
原始方法:


1

2

3

4

5

6

7

8

9

10


var obj = {

name: ‘geyulong‘,

age: 0

};

var obj2 = new Object();

obj2.name = obj.name;

obj2.age = obj.age;

obj.name = "gaiyulong";

console.log(obj); // Object {name: ‘geyulong‘, age: 0}

console.log(obj2); // Object {name: ‘gaiyulong‘, age: 0}

当然我们是要封装一个方法来实现深拷贝。


1

2

3

4

5

6

7

8

9

10

11

12


var deepCopy = function(source) {

var result = {};

for(var key in source) {

if(typeof source[key] === ‘object‘) {

result[key] = deepCopy(source[key])

} else {

result[key] = source[key]

}

}

return result;

}

var obj2 = deepCopy(obj);

ShareComments

时间: 2024-10-24 16:20:13

JavaScript 深浅拷贝的相关文章

Javascript深浅拷贝

Javascript有六种基本数据类型(也就是简单数据类型),它们分别是:Undefined,Null,Boolean,Symbol,Number和String.还含有一种复杂数据类型,就是对象 注意Undefined和Null的区别,Undefined类型只有一个值,就是undefined,Null类型也只有一个值,也就是nullUndefined其实就是已声明未赋值的变量输出的结果null其实就是一个不存在的对象的结果 var a; console.log(a)//undefined con

《关于JavaScript的深浅拷贝》

JavaScript深浅拷贝 一,序言: 这两天在前辈的代码里看到了object.assign(),当时一直不明白为啥要用这个,知道昨天看了深浅拷贝,恍然大悟!看了好几篇博客都是关于深浅拷贝的,还有详细讲object.assign(),把自己所学到的写一下,也引用一下这两篇博主的文稿,写的是贼棒! 二,深浅拷贝(只针对Object和Array这样的引用数据类型的)[ 详见:https://github.com/ljianshu/Blog/issues/5 ] 1.数据类型 ·数据类型分为基本数据

[记录] JavaScript 中的深浅拷贝(克隆)

浅拷贝和深拷贝针对的是Object.Array这样复杂的引用类型数据 简单说:浅拷贝只复制一层的属性,而深拷贝则递归复制所有层级的属性 一.浅拷贝 1 function clone(origin, target) { 2 var result = target || {}; 3 for ( var prop in origin ){ 4 target[prop] = origin[prop]; 5 } 6 return result; 7 } 如果对象的属性值是数组或对象,实际上,存储的值是一个

js的深浅拷贝

js数据类型包括5种简单数据类型(或者基本数据类型):Undefined, Null, Number, String, Boolean, 指的是保存在栈内存中的简单数据段.还有一种复杂数据类型(引用数据类型):Object Function Array,指的是那些保存在堆内存中的对象. 深浅拷贝只是针对Object,Array这样的复杂对象.javascript存储对象都是存地址. 对象: 浅拷贝只是针对对象的各个属性进行一次复制,复制前后两个属性指向的还是同一块内存地址 深拷贝不仅对各个属性进

python学习笔记4:基础(集合,collection系列,深浅拷贝)

转载至:http://www.cnblogs.com/liu-yao/p/5146505.html 一.集合 1.集合(set): 把不同的元素组成一起形成集合,是python基本的数据类型.集合元素(set elements):组成集合的成员 python的set和其他语言类似, 是一个无序不重复元素集, 基本功能包括关系测试和消除重复元素. 集合对象还支持union(联合), intersection(交), difference(差)和sysmmetric difference(对称差集)

Python3.5(十)深浅拷贝问题

[可变对象-不可变对象] 在Python中不可变对象指:一旦创建就不可修改的对象,包括字符串,元祖,数字 在Python中可变对象是指:可以修改的对象,包括:列表.字典 >>> L1 = [2,3,4] #L1变量指向的是一个可变对象:列表 >>> L2 = L1 #将L1值赋给L2后,两者共享引用同一个列表对象[1,2,3,4] >>> L1[0] = 200 #因为列表可变,改变L1中第一个元素的值 >>> L1; L2 #改变后

C++模板实现动态顺序表(更深层次的深浅拷贝)与基于顺序表的简单栈的实现

前面介绍的模板有关知识大部分都是用顺序表来举例的,现在我们就专门用模板来实现顺序表,其中的很多操作都和之前没有多大区别,只是有几个比较重要的知识点需要做专门的详解. 1 #pragma once 2 #include<iostream> 3 #include<string> 4 #include<stdlib.h> 5 using namespace std; 6 7 template <class T> 8 class Vector 9 { 10 publ

Python深浅拷贝

深浅拷贝 深浅拷贝分为两部分,一部分是数字和字符串另一部分是列表.元组.字典等其他数据类型. 数字和字符串 对于数字和字符串而言,赋值.浅拷贝和深拷贝无意义,因为他们的值永远都会指向同一个内存地址. # 导入copy模块>>> import copy# 定义一个变量var1>>> var1 = 123# 输出var1的内存地址>>> id(var1)1347747440>>> var2 = var1# var2的内存地址和var1相同

Python 从零学起(纯基础) 笔记 之 深浅拷贝

深浅拷贝 1. import  copy#浅拷贝copy.copy()#深拷贝copy.deepcopy()#赋值 = 2.   对于数字和字符串而言,赋值.浅拷贝和深拷贝无意义,因为其永远指向同一个内存地址. 对于 字典.元组.列表 而言,进行赋值.浅拷贝和深拷贝时,其内存地址的变化是不同的. 浅拷贝,在内存中只额外创建第一层数据. 深拷贝,在内存中将所有的数据重新创建一份(排除最后一层,即:Python内部对字符串和数字的优化)   1 import copy 2 n1 = {"k1&quo