【Python】浅拷贝、深拷贝

  深拷贝和浅拷贝都是对象的拷贝,都会生成一个看起来相同的对象,本质的区别是拷贝出来的对象的地址是否和原对象一样,也就是地址的复制还是值的复制的区别

可变对象:一个对象在不改变其所指向的地址的前提下,可以修改其所指向的地址中的值;
不可变对象:一个对象所指向的地址上值是不能修改的,如果你修改了这个对象的值,那么它指向的地址就改变了,相当于你把这个对象指向的值复制出来一份,然后做了修改后存到另一个地址上了,但是可变对象就不会做这样的动作,而是直接在对象所指的地址上把值给改变了,而这个对象依然指向这个地址。

  可变元素的浅拷贝:拷贝出来的新对象的地址和原对象是不一样的,但是新对象里面的可变元素(如列表)的地址和原对象里的可变元素的地址是相同的,即,对象里的可变元素作为深层次的数据结构并没有被拷贝到新地址里面去,而是和原对象里的可变元素指向同一个地址,所以在新对象或原对象里对这个可变元素做修改时,。

区别说明 (引用 菜鸟教程)

  • b = a: 赋值引用,a 和 b 都指向同一个对象


    赋值引用
  • b = a.copy(): 浅拷贝, a 和 b 是一个独立的对象,但他们的子对象还是指向统一对象(是引用)。


    浅拷贝

以下方式得到的拷贝都是浅拷贝:
● 切片操作[:]
● 调用列表、字典、集合的方法copy()
● 调用内置函数List()、dict()、set.
● 调用标准库模块copy中的函数copy()

  • b = copy.deepcopy(a): 深度拷贝, a 和 b 完全拷贝了父对象及其子对象,两者是完全独立的。


    深拷贝

测试(引用 菜鸟教程)

测试

拷贝的特殊情况:

  • 对于没有拷贝这一说。也就是说,对于这些类型,"obj is copy.copy(obj)" 、"obj is copy.deepcopy(obj)"
  • 如果元祖变量只包含原子类型对象,则不能深拷贝。

总结:

  • Python中对象的赋值都是进行对象引用(内存地址)传递
  • 使用copy.copy(),可以进行对象的浅拷贝,它复制了对象,但对于对象中的元素,依然使用原始的引用.
  • 如果需要复制一个容器对象,以及它里面的所有元素(包含元素的子元素),可以使用copy.deepcopy()进行深拷贝
  • 对于非容器类型(如数字、字符串、和其他'原子'类型的对象)没有被拷贝一说
  • 如果元祖变量只包含原子类型对象,则不能深拷贝,看下面的例子

你可能感兴趣的:(【Python】浅拷贝、深拷贝)