深浅拷贝
一:赋值
在Python中,所谓的赋值实际上就是对象引用的传递而已,当创建一个对象的时候,再赋值给另外一个变量的时候,并不是赋值给另一个变量。而是把这个变量在地址空间的id地址值传递给另一个变量,简单的说就是拷贝了这个对象的引用。
a = 11 b = a print(b) # 11 print(id(a)) # 495218464 print(id(b)) # 495218464
二:浅拷贝
特点:浅拷贝是对一个对象父级(外层)的拷贝,并不会拷贝子级(内部)。
情况讨论:
第一种:
(1)针对最外层为可变对象的时候 会开辟新的地址空间
import copy a = [11,22,33,44] b = copy.copy(a) print(b) # 拷贝之后的值 [11, 22, 33, 44] print(id(a)) # 166144008 print(id(b)) # 166629640
PS:可以看出拷贝之后 开辟新的内存空间
(2)原值改变不会影响拷贝后的值
import copy a = [11,22,33,44] b = copy.copy(a) print(b) # 拷贝之前的值 [11, 22, 33, 44] a.append(123123) # 修改原值 print(a) # 原值修改之后的值 [11, 22, 33, 44, 123123] print(b) # [11, 22, 33, 44] print(id(a)) # 166144008 print(id(b)) # 166629640
PS:原值修改 不会影响拷贝之后的值
第二种:
(1)当最外层为不可变类型的时候 会引用原来的地址
import copy a = 'qweqweqweqwe' b = copy.copy(a) print(b) # 拷贝之后的值 qweqweqweqwe print(id(a)) # 166632176 print(id(b)) # 166632176
(2)当最外层为可变类型的时候 原值改变 拷贝之后的值也会改变
import copy a = ([1,2,3],) b = copy.copy(a) print(b) # 拷贝之后的值 ([1, 2, 3],) a[0].append(123123123) # 原值修改 print(a) # 修改之后的原值 ([1, 2, 3, 123123123],) print(b) # 修改之后的拷贝的值 ([1, 2, 3, 123123123],) print(id(a)) # 33803008 print(id(b)) # 33803008
三:深拷贝
特点:深拷贝对一个对象是所有层次的拷贝(递归),内部和外部都会被拷贝过来。
情况讨论
第一种:
(1)当最外层为可变对象的时候 无论内部是什么类型 都会完全拷贝 开辟新的内存空间
import copy a = [1,2,3,3] b = copy.deepcopy(a) print(b) # [1, 2, 3, 3] print(id(a)) # 166471688 print(id(b)) # 166957320
PS:拷贝之后 开辟了新的内存空间
(2)当原值改变 拷贝之后的值 不会被改变
import copy a = [1,2,3,3] b = copy.deepcopy(a) print(b) # [1, 2, 3, 3] a.append(123123) print(a) # [1, 2, 3, 3, 123123] 修改之后的值 print(b) # [1, 2, 3, 3] 不会被影响 print(id(a)) # 166471688 print(id(b)) # 166957320
第二种
(1):当外层对象为不可变对象 内层对象为可变对象的时候 会开辟新的内存地址
import copy a = ([1,2,3],) b = copy.deepcopy(a) print(b) # ([1, 2, 3],) print(id(a)) # 2083584 print(id(b)) # 5856728
PS:拷贝之后 开辟了新的内存空间
(2):当外层对象为不可变对象 内层对象为可变对象的时候 原值改变 不会改变拷贝之后的值
import copy a = ([1,2,3],) b = copy.deepcopy(a) print(b) # ([1, 2, 3],) a[0].append(12312312) # 修改原值 print(a) # ([1, 2, 3, 12312312],) 修改之后的原值 print(b) # 原值修改 拷贝值不变 print(id(a)) # 2083584 print(id(b)) # 5856728
(3):当外层对象为不可变对象 内层对象为不可变对象的时候 会引用原始内存地址
import copy a = (1,2,3) b = copy.deepcopy(a) print(b) # (1, 2, 3) print(id(a)) # 166811616 print(id(b)) # 166811616