关于Python深拷贝和浅拷贝的区别

深入浅出的对Python的深拷贝和浅拷贝进行区分

在Python中,对象赋值实际上是对象的引用。当创建一个对象,然后把它赋给另一个变量的时候,python并没有拷贝这个对象,而只是拷贝了这个对象的引用

通常有三种方法:

赋值引用

  • 直接赋值,默认浅拷贝传递对象的引用而已,原始列表改变,被赋值的b也会做相同的改变,a和b都指向同一个对象。

直接赋值

1
2
3
4
5
6
7
8
>>> a=[1,2,3,["a","b"]]
>>> b=a
>>> print b
[1, 2, 3, ['a', 'b']]
>>> a.append(5)
>>> print a;print b
[1, 2, 3, ['a', 'b'], 5]
[1, 2, 3, ['a', 'b'], 5]

浅拷贝

  • copy浅拷贝,没有拷贝子对象,所以原始数据改变,子对象会改变

浅拷贝

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
>>> import copy
>>> a=[1,2,3,["a","b"]]
>>> c=copy.copy(a)
>>> print a;print c
[1, 2, 3, ['a', 'b']]
[1, 2, 3, ['a', 'b']]
>>> a.append(5)
>>> print a;print c
[1, 2, 3, ['a', 'b'], 5]
[1, 2, 3, ['a', 'b']]

>>> a[3]
['a', 'b']
>>> a[3].append('cccc')
>>> print a;print c
[1, 2, 3, ['a', 'b', 'cccc'], 5]
[1, 2, 3, ['a', 'b', 'cccc']] 里面的子对象被改变了

深拷贝

  • 深拷贝,包含对象里面的自对象的拷贝,所以原始对象的改变不会造成深拷贝里任何子元素的改变

深拷贝

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
>>> import copy
>>> a=[1,2,3,["a","b"]]
>>> d=copy.deepcopy(a)
>>> print a;print d
[1, 2, 3, ['a', 'b']]
[1, 2, 3, ['a', 'b']]始终没有改变
>>> a.append(5)
>>> print a;print d
[1, 2, 3, ['a', 'b'], 5]
[1, 2, 3, ['a', 'b']]始终没有改变
>>> a[3]
['a', 'b']
>>> a[3].append("ccccc")
>>> print a;print d
[1, 2, 3, ['a', 'b', 'ccccc'], 5]
[1, 2, 3, ['a', 'b']] 始终没有改变