今天写程序,人为制造了一个由浅拷贝引起的bug,有必要归纳一下。先附上源代码: class PerformanceTest(object):
def __init__(self):
.......
self.basic_path_list=[]
....... #这就是一个生成基础路径名的函数,从26个字符中选择五个字符加上‘/'构成基础路径
def _get_basic_path_list(self,path_num):
.......
self.basic_path_list.append(path)
....... .......
#这是一个对用Elementtree实现的xml树进行测试的测试函数,首先需要的就是生成测试路径列表
#建立一颗结点数目为test_num,满child_num叉树
def add_performance_test(self,child_num,test_num):
.......
#mid_list=deepcopy(self.basic_path_list)
#path_list=deepcopy(self.basic_path_list)
mid_list=self.basic_path_list
path_list=self.basic_path_list
while len(path_list)<test_num:
child_list=[]
for mid_path in mid_list:
for spath in self.basic_path_list:
path=mid_path+spath
child_list.append(path) if len(path_list)+len(child_list)>test_num:
path_list+=child_list[:test_num-len(path_list)]
break
else:
path_list+=child_list mid_list=child_list #接下来就是将path_list中所有元素添加到自己定义的xml树中,代码略
......
 
    结果,我在执行add_performance_test(2,100)函数后发现,生成的xml文件中目录树居然有9层。
    100=1+2+4+8+16+32+37,应该是7层,却生成了9层目录,bug在哪里? 
    经过一段时间的调试后,确信是self.basic_path_list值在执行过程中起了变化,这是绝对不应该的。后来回想起初学python时看到的关于浅拷贝和深拷贝的内容,恍然大悟。mid_list和path_list在赋值的时候均执行的是浅拷贝,path_list在循环中改变时,也改变了self.basic_path_list值。 找到了问题,在赋值时将浅拷贝替换为深拷贝,代码就正常运行了。
 

这个错误给我敲响了警钟,像这样的bug代码不会报错,但根本得不到需要的结果。我仔细检查了以前写的代码,还发现了几处类似的浅拷贝,尤其是运行那些代码可以得要预期结果,但为了保险起见,我还是将其均替换为深拷贝。

在最后摘录一部分python核心编程中对于浅拷贝和深拷贝的描述,望以后写程序时引以为戒。

序列类型的可以通过三种方式实现浅拷贝,浅拷贝也是默认的拷贝类型:(1)完全切片操作;(2)利用工厂函数,比如list()等;(3)使用copy模块中的copy()函数。然而对于非容器类型没有拷贝这这一说。

有几点关于拷贝操作的警告。第一,非容器类型(比如数字,字符串和其他"原子"类型的对象,像代码,类型和xrange对象等)没有深拷贝一说,浅拷贝是用完全切片操作来完成的.第二,如果元组变量只包含原子类型对象,对它的深拷贝将不会进行.

python浅拷贝与深拷贝的更多相关文章

  1. python 浅拷贝和深拷贝(9)

    何谓浅拷贝/深拷贝,说得直白一点,其实就是数据拷贝,两者到底有什么区别呢?听着就挺迷糊的,python开发项目的时候说不定你就能碰上这样的坑~~     一.普通的变量赋值 我们平常使用的变量赋值就是 ...

  2. python浅拷贝和深拷贝

    博文参考地址:https://blog.csdn.net/qq_20084101/article/details/82925067 最近在撸码的时候发现了一个严重的问题: a = [1,2] c = ...

  3. Python浅拷贝与深拷贝(可变对象与不可变对象)

    第一次遇到深拷贝和浅拷贝的问题是用python在一个for循环中对一个list赋值,使用的语句是 a = b 这个b会不断带入循环,每次计算得到,最后发现list乱七八糟的,后来才发现,python中 ...

  4. python浅拷贝与深拷贝浅析

    首先我们要明确,python中大多数都是浅拷贝,我们先说原因: 1.时间花费更少 2.内存更小 3.效率更高,浅拷贝只拷贝顶层数据,一般情况下比深拷贝效率高. 容器(如列表)切片是浅拷贝

  5. 学习Python一年,这次终于弄懂了浅拷贝和深拷贝

    官方文档:copy主题 源代码: Lib/copy.py 话说,网上已经有很多关于Python浅拷贝和深拷贝的文章了,不过好多文章看起来还是决定似懂非懂,所以决定用自己的理解来写出这样一篇文章. 当别 ...

  6. 【转】Python中的赋值、浅拷贝、深拷贝介绍

    这篇文章主要介绍了Python中的赋值.浅拷贝.深拷贝介绍,Python中也分为简单赋值.浅拷贝.深拷贝这几种"拷贝"方式,需要的朋友可以参考下   和很多语言一样,Python中 ...

  7. 关于python中赋值、浅拷贝、深拷贝之间区别的深入分析

    当重新学习了计算机基础课程<数据结构和算法分析>后再来看这篇自己以前写的博文,发现错误百出.python内置数据类型之所以会有这些特性,归根结底是它采用的是传递内存地址的方式,而不是传递真 ...

  8. python中的深拷贝与浅拷贝

    深拷贝和浅拷贝 浅拷贝的时候,修改原来的对象,浅拷贝的对象不会发生改变. 1.对象的赋值 对象的赋值实际上是对象之间的引用:当创建一个对象,然后将这个对象赋值给另外一个变量的时候,python并没有拷 ...

  9. python的浅拷贝和深拷贝

    python对象有两种拷贝的形式:浅拷贝和深拷贝. 在<python核心编程>中看到对这两种拷贝的分析,觉得十分收益,所以记录在此. id()方法:id()方法可以查看某个对象的ID,类似 ...

随机推荐

  1. IOException 简单解决方法

    java.lang.IllegalStateException异常解决方法 这个异常大多数是由文件读取,下载时抛出,但是偶尔也会由类型转换时异常抛出此异常. 错误:Optional int param ...

  2. E20170623-ts

    filter   n. 滤波器; 滤光器; 滤色镜; [化] 过滤器; mass   n. 大量,大多; 块,堆,团; [物理学] 质量; 弥撒曲; assignment  n. 分给,分配; 任务, ...

  3. [Swift通天遁地]四、网络和线程-(15)程序内购功能

    ★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★➤微信公众号:山青咏芝(shanqingyongzhi)➤博客园地址:山青咏芝(https://www.cnblogs. ...

  4. CSS-类和ID选择器的区别

    学习了类选择器和ID选择器,我们会发现他们之间有很多的相似处,是不是两者可以通用呢?我们不要着急先来总结一下他们的相同点和不同点: 相同点:可以应用于任何元素不同点: 1.ID选择器只能在文档中使用一 ...

  5. 为什么选择Sqoop?(三)

    为什么选择 Sqoop? 通常基于三个方面的考虑: 1.它可以高效.可控地利用资源,可以通过调整任务数来控制任务的并发度.另外它还可以配置数据库的访问时间等等. 2.它可以自动的完成数据类型映射与转换 ...

  6. Android热修复方案比较

    热修复的特点:无需重新发版,实时高效热修复:用户无感知修复,无需下载新的应用,代价小: 修复成功率高,把损失降到最低. 一.热修复开源方案和使用情况 方案名称 方案开发公司 开发时间 Github星评 ...

  7. Paint、Canvas

    1.Canvas类 public class Canvas { public static final int ALL_SAVE_FLAG = 31; /** @deprecated */ @Depr ...

  8. [转帖]c++ 面试整理

    1. 继承方式 public    父类的访问级别不变 protected    父类的public成员在派生类编程protected,其余的不变 private        父类的所有成员变成pr ...

  9. WEB文件上传之apache common upload使用(一)

    文件上传一个经常用到的功能,它有许多中实现的方案. 页面表单 + RFC1897规范 + http协议上传 页面控件(flash/html5/activeX/applet) + RFC1897规范 + ...

  10. 【PostgreSQL-9.6.3】分区表

    PostgreSQL中的分区表是通过表继承来实现的(表继承博客http://www.cnblogs.com/NextAction/p/7366607.html).创建分区表的步骤如下: (1)创建“父 ...