Python编程中的反模式实例分析


Posted in Python onDecember 08, 2014

本文实例讲述了Python编程中的反模式。分享给大家供大家参考。具体分析如下:

Python是时下最热门的编程语言之一了。简洁而富有表达力的语法,两三行代码往往就能解决十来行C代码才能解决的问题;丰富的标准库和第三方库,大大节约了开发时间,使它成为那些对性能没有严苛要求的开发任务的首选;强大而活跃的社区,齐全的文档,也使很多编程的初学者选择了它作为自己的第一门编程语言。甚至有国外的报道称,Python已经成为了美国顶尖大学里最受欢迎的编程入门教学语言。

要学好一门编程语言实属不易,在初学阶段,就纠正一些错误的做法,对今后的深入学习至关重要。有一位叫Constantine Lignos的博主,他是宾夕法尼亚儿童医院放射研究部门的博士后研究员,他最近撰写了一篇很有意义的文章,列举了初学Python的学生们最常犯的错误,并对这些错误进行了分类和剖析,其内容提纲挈领,非常值得每个Python初学者学习。

这篇文章给出了一些在Python初学者中很常见的反模式,反模式通常是指那些不符合习惯或者会导致糟糕后果的用法。Lignos把他总结的反模式分成了四大类——迭代、性能、变量的漏洞和编程风格。下面我们逐一来看一个例子,理解这些反模式到底“反”在什么地方。

一、迭代

当我们需要简单迭代一个数量范围的时候,Python给了我们一个非常好用的函数:range。Lignos观察到有些初学者喜欢用range来迭代列表的下表,像下面这种形式:

for i in range(len(alist)):

    print alist[i]

这代码现在还没什么问题,但已经不符合Python的习惯了。但下面的代码就有问题了:
alist = ['her', 'name', 'is', 'rio']

for i in range(0, len(alist) - 1): # 漏掉了最后一个

    print i, alist[i]

我们可以看一下Python官方文档range的示例:
>>> range(1, 11)

[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

range的右区间是不包含在内的,如果受了直觉或其他编程语言的影响,再减1就不对了。Lignos还列举了其他几种错误的迭代模式,我们只要记住,range应该用在迭代一个数量范围。

二、性能

Lignos给出了两段代码:

lyrics_list = ['her', 'name', 'is', 'rio']

words = make_wordlist()

for word in words:

    if word in lyrics_list: # 线性时间

        print word, "is in the lyrics"


lyrics_set = set(lyrics_list)

words = make_wordlist()

for word in words:

    if word in lyrics_set: # 常数时间

        print word, "is in the lyrics"

哪种模式效率更高?Lignos注释已经给出了答案。注释的意思是,判断一个元素是否在一组元素中存在,使用list的算法复杂度是O(n),而使用set的算法复杂度是O(1)。那是否set永远是优于list?在其他情况下,应该用哪个数据结构?Python官方Wiki有一份专门各个数据结构操作的时间复杂度的文档供参考,知道参考这份文档比答案本身更重要。至于为什么,只有Python的源码才能告诉我们。

三、变量的漏洞

初学者往往会假设一些不该假设的前提,对一些异常流程考虑不周。Lignos也给了一个例子:

for idx, value in enumerate(y):

    if value > max_value:

        break

processList(y, idx)

这里y如果是空的,那就出问题了,因为idx根本得不到定义,最终我们会得到一个NameError的异常。比较好的做法是给idx一个默认的错误值,在C语言里面我们经常喜欢用-1。下面的代码就考虑得比较全面:
def find_item(item, alist):

    # 对Python来说None比-1可能更好点

    result = -1

    for idx, other_item in enumerate(alist):

        if other_item == item:

            result = idx

            break

    return result

四、代码风格

Python有一份代码风格指导文档PEP 8,这些规则都是有道理的。当初学者不明白为什么的时候,最好的做法就是尽量遵守它,等到有更深入的理解了就会豁然开朗,同事也会明白什么时候可以打破规则。Lignos引用了这份文档的一些例子,比如,如何测试一个变量是否为空,如果测试一个变量是否为None等等。

以上分析了这篇文章中的一些例子,如果希望全面了解,请查看原文。想要学好一门编程语言,学会语法是远远不够的,必须逐步理解语言所依赖的CPU体系结构、编译器/解释器/虚拟机等内容。Lignos这篇文章虽然没有深入剖析Python的实现,但是对于入门者的帮助是非常明显的,当初学者有了一定经验后,对一些问题都可以做深入挖掘,引出Python实现层面的问题。

希望本文所述对大家的Python程序设计有所帮助。

Python 相关文章推荐
Python 创建子进程模块subprocess详解
Apr 08 Python
python实现实时监控文件的方法
Aug 26 Python
R vs. Python 数据分析中谁与争锋?
Oct 18 Python
Python SQL查询并生成json文件操作示例
Aug 17 Python
对python添加模块路径的三种方法总结
Oct 16 Python
Python中is和==的区别详解
Nov 15 Python
django和vue实现数据交互的方法
Aug 21 Python
python实现宿舍管理系统
Nov 22 Python
python opencv pytesseract 验证码识别的实现
Aug 28 Python
Django中和时区相关的安全问题详解
Oct 12 Python
python爬不同图片分别保存在不同文件夹中的实现
Apr 02 Python
Python数据分析入门之教你怎么搭建环境
May 13 Python
Python实现拼接多张图片的方法
Dec 01 #Python
python字符串替换的2种方法
Nov 30 #Python
Python中3种内建数据结构:列表、元组和字典
Nov 30 #Python
Python函数中定义参数的四种方式
Nov 30 #Python
Python 自动补全(vim)
Nov 30 #Python
给Python IDLE加上自动补全和历史功能
Nov 30 #Python
让 python 命令行也可以自动补全
Nov 30 #Python
You might like
Php中用PDO查询Mysql来避免SQL注入风险的方法
2013/04/25 PHP
Fatal error: Allowed memory size of 134217728 bytes exhausted (tried to allocate 2611816 bytes)
2014/11/08 PHP
php基于自定义函数记录log日志方法
2017/07/21 PHP
Laravel 前端资源配置教程
2019/10/18 PHP
JavaScript Archive Network 集合
2007/05/12 Javascript
js 禁止选择功能实现代码(兼容IE/Firefox)
2010/04/23 Javascript
asp.net网站开发中用jquery实现滚动浏览器滚动条加载数据(类似于腾讯微博)
2012/03/14 Javascript
深入理解JavaScript系列(14) 作用域链介绍(Scope Chain)
2012/04/12 Javascript
浅析JavaScript中的类型和对象
2013/11/29 Javascript
详解AngularJs中$sce与$sceDelegate上下文转义服务
2016/09/21 Javascript
JS实现拖动滚动条评分的效果代码分享
2016/09/29 Javascript
jQuery插件HighCharts绘制简单2D柱状图效果示例【附demo源码】
2017/03/21 jQuery
使用 jQuery 实现表单验证功能
2017/07/05 jQuery
jquery使用iscorll实现上拉、下拉加载刷新
2017/10/26 jQuery
微信小程序如何像vue一样在动态绑定类名
2018/04/17 Javascript
详解微信小程序文件下载--视频和图片
2019/04/24 Javascript
发布订阅模式在vue中的实际运用实例详解
2019/06/09 Javascript
微信小程序自定义弹窗实现详解(可通用)
2019/07/04 Javascript
JavaScript实现背景自动切换小案例
2019/09/27 Javascript
[35:55]完美世界DOTA2联赛PWL S3 Rebirth vs CPG 第一场 12.11
2020/12/13 DOTA
Python使用pygame模块编写俄罗斯方块游戏的代码实例
2015/12/08 Python
Python入门必须知道的11个知识点
2018/03/21 Python
对Python 3.5拼接列表的新语法详解
2018/11/08 Python
树莓派使用USB摄像头和motion实现监控
2019/06/22 Python
基于Python函数和变量名解析
2019/07/19 Python
python是否适合网页编程详解
2019/10/04 Python
python使用多线程查询数据库的实现示例
2020/08/17 Python
浏览器实现移动端高性能css3动画(开启gpu加速)
2013/12/23 HTML / CSS
什么是Linux虚拟文件系统VFS
2015/08/25 面试题
详解如何解决使用JSON.stringify时遇到的循环引用问题
2021/03/23 Javascript
哈理工毕业生的求职信
2013/12/22 职场文书
派出所正风肃纪剖析材料
2014/10/10 职场文书
幼儿教师辞职信范文
2015/03/02 职场文书
2015领导干部廉洁自律工作总结
2015/07/23 职场文书
导游经典开场白——导游词
2019/04/17 职场文书
Python数据分析入门之教你怎么搭建环境
2021/05/13 Python