Python深拷贝与浅拷贝(Python系列09)

前言:在python中深拷贝和浅拷贝它们的区别是什么,在什么情况下使用浅拷贝好,又在情况下不使用深拷贝可能会出现问题,想要弄明白,我们得从内存下手。

我们先来看下面这段代码:

list_old = [1, 2, 3, 4, 5]
list_new = list_old
list_new[0] = 5
print(list_old)
print(list_new)

# 运行结果
# [5, 2, 3, 4, 5]
# [5, 2, 3, 4, 5]

 可以看到列表 list_old 改变的时候,list_new也改变了,那这是为什么呢,我们来看看内存里是如何变化的吧。

list_new = list_old不属于拷贝,仅仅是list_old把列表数据的地址赋值给了变量list_new,所以list_new和list_old中存储的内存地址是相同的,所以在数据发生变化的时候,它们会同时变化。

业务需求就是希望list_new变化,list_old保持不变,这个时候应该如何解决?

浅拷贝:

list_old = [1, 2, 3, 4, 5]
# list_new = list_old.copy()
list_new = [:]
list_new[0] = 5
print(list_old)
print(list_new)

# 运行结果
# [1, 2, 3, 4, 5]
# [5, 2, 3, 4, 5]

如上述代码,我们可以用切片或者python的内置函数copy对列表进行浅拷贝,为什么浅拷贝后就能达到上述的业务需求呢?让我们来看看内存图吧。

如上图所示,浅拷贝创建了一个新的列表对象,当list_new里的数据地址发生改变的时候,并不会影响到list_old。

那如果我把代码改一下,浅拷贝还能完成我们的需求吗?

list_old = [[1, 2], 2, 3, 4, 5]
list_new = list_old[:]
list_new[0][1] = 1
print(list_old)
print(list_new)

# 运行结果
# [[1, 1], 2, 3, 4, 5]
# [[1, 1], 2, 3, 4, 5]

在这段代码中又出现了上面的问题,list_new改变的时候list_old也发生改变,我们来看看内存的变化吧。

我们可以看到,浅拷贝时当列表中的元素有可变类型时,还是会出现上面提到的情况,这个时候我们应该如何解决呢?

深拷贝:

import copy

list_old = [[1, 2], 2, 3, 4, 5]
list_new = copy.deepcopy(list_old)
list_new[0][1] = 1
print(list_old)
print(list_new)

# 运行代码
# [[1, 2], 2, 3, 4, 5]
# [[1, 1], 2, 3, 4, 5]

内存图奉上:

深拷贝拷贝所有层的数据,拷贝后的数据完全独立。

深浅拷贝的对比:

1.深拷贝拷贝所有层的数据,拷贝后的数据完全独立。

        优点是修改数据时互不影响,缺点是占用内存较大。

2.浅拷贝拷贝的是第一层数据,共享深层数据。

        优点是占用内存较小,缺点是修改深层数据互相影响。

需要拷贝深层数据时使用深拷贝,否则使用浅拷贝。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值