zoukankan      html  css  js  c++  java
  • python--关于赋值与深浅拷贝的认识

      作为一个自学python的小白,平时用到深浅拷贝的机会很少,因此对其也是一知半解。但是,作为一个立志成为后端工程狮的男人,眼里揉不了沙子,于是专门花时间补了补课,在此记录一下学习心得。


        在讲深浅拷贝之前,首先看一下赋值

    1 a = "小新"
    2 b = a
    3 print(b)
    4 >> "小新"
    5 b = "辣眼睛"  # 对b重新赋值
    6 print(b)
    7 >> "辣眼睛"
    8 print(a) 9 >> "小新" # a没有变

      这个肯定是没有问题的,接下来用列表试一下:

    1 a = ["小新", "辣眼睛"]
    2 b = a
    3 print(b)
    4 >> ["小新", "辣眼睛"]
    5 b[1] = "DE"  # 对b[1]重新赋值
    6 print(b)
    7 >> ["小新", "DE"]
    8 print(a)
    9 >> ["小新", "DE"] # WTF,a怎么会变?

      相信有不少小白会跟我一样,在这里就懵圈了,a为什么会变呢,现在来探究一下原理,当我们创建一个变量时,会为变量的值在内存开辟一块空间,这块空间有一个地址(类似于你家的门牌号),变量拿着这个地址找到它赋予的值。废话不多说,看图:

     

      那么变量如果是列表或者字典、元组,同样如此,不过这个时候,变量指向的就不是列表中的内容了,因为变量只能指向一个内存地址,而列表中的元素可以有多个,此时变量指向的是列表的内存地址。列表相当于一个盒子,列表中的元素也会有自己单独的内存地址,元素的内存地址就放在盒子里面,b将列表中的元素改变了之后,盒子里装着的相应元素的内存地址也会发生变化,a再来看盒子来拿的时候,内存地址就是变化之后的了。如图:

      接下来看一下浅拷贝:

     1 a = ["小新", "辣眼睛", [0,1]]
     2 b = a.copy()
     3 print(b)
     4 >> ["小新", "辣眼睛", [0,1]]
     5 b[1] = "DE"
     6 print(a)  # 我们看下a
     7 >> ["小新", "辣眼睛", [0,1]] # a没有变
     8 b[2][0]=""
     9 print(a)  # 再来看下a
    10 >> ["小新", "辣眼睛", [“零”,1]] # WTF*2,a怎么变了

      接下来我们看一下浅拷贝的原理:

      b = a.copy(), 这时a 和 b 是一个独立的对象,分别指向不同的内存地址,也就是说a和b现在是两个不同的盒子。所以我们在对b[1]重新赋值了之后,并没有影响到a,但是你可能有疑问了,对b[2][0]重新赋值后,为什么会影响到a呢,这是因为b在拷贝之后,不仅新创建了一个盒子,同时也把a盒子中的内存地址都拿了过来,对b[1]重新赋值,修改了b盒子里面的内存地址,a盒子的内存地址并没有发生变化,所以a[1]不变。对b[2]重新赋值,其实a[2]也不会变,如果是对b[2][0]重新赋值,a[2][0]为什么也变了呢,这是因为浅拷贝只复制到了第一层,也就是b[0]、b[1]、b[2]这一层,如图:

        

      透过上图可以看到,浅拷贝只是复制了第一层,而且只是拷贝了元素的内存地址,如果想要把a中的内容全部复制到b中,我们要借助于深拷贝。

      深拷贝

      深拷贝不只是新建一个盒子b(也就是内存对象b),而且递归的把a中的元素全部拷贝。深拷贝会将第一层中的列表、元组或字典赋予一个新的内存地址,也就是这个改动,使得我们修改b的同时,不会改变a。

      扩展

      b = a[:] 也可以将列表a的值赋给b, 其原理跟浅拷贝相同,大家可以测试一下。

  • 相关阅读:
    【面积并】 Atlantis
    【动态前k大 贪心】 Gone Fishing
    【复杂枚举】 library
    【双端队列bfs 网格图建图】拯救大兵瑞恩
    【奇偶传递关系 边带权】 奇偶游戏
    【权值并查集】 supermarket
    CF w4d3 A. Pythagorean Theorem II
    CF w4d2 C. Purification
    CF w4d2 B. Road Construction
    CF w4d2 A. Cakeminator
  • 原文地址:https://www.cnblogs.com/jiaxiaoxin/p/8399626.html
Copyright © 2011-2022 走看看