python基础——调试

  

  程序能一次写完并正常运行的概率很小,基本不超过1%。总会有各种各样的bug需要修正。有的bug很简单,看看错误信息就知道,有的bug很复杂,我们需要知道出错时,哪些变量的值是正确的,哪些变量的值是错误的,因此,需要一整套调试程序的手段来修复bug。

  第一种方法简单直接粗暴有效,就是用print()把可能有问题的变量打印出来看看

def foo(s):
n = int(s)
print('>>> n = %d' % n)
return 10 / n def main():
foo('') main()

  执行后在输出中查找打印的变量值:

>>> n = 0
Traceback (most recent call last):
...
ZeroDivisionError: integer division or modulo by zero

  用print()最大的坏处是将来还得删掉它,想想程序里到处都是print(),运行结果也会包含很多垃圾信息。所以,我们又有第二种方法。

断言

  凡是用print()来辅助查看的地方,都可以用断言(assert)来替代

ef foo(s):
n = int(s)
assert n != 0, 'n is zero!'
return 10 / n def main():
foo('')

  assert的意思是,表达式n != 0应该是True,否则,根据程序运行的逻辑,后面的代码肯定会出错。

  如果断言失败,assert语句本身就会抛出AssertionError

    

  程序中如果到处充斥着assert,和print()相比也好不到哪去。不过,启动Python解释器时可以用-O参数来关闭assert

    

  关闭后,可以把所有的assert语句当成pass来看。

logging

  把print()替换为logging是第3种方式,和assert比,logging不会抛出错误,而且可以输出到文件:

import logging

s = ''
n = int(s)
logging.info('n = %d' % n)
print(10 / n)

  logging.info()就可以输出一段文本。运行,发现除了ZeroDivisionError,没有任何信息。怎么回事?

    

  别急,在import logging之后添加一行配置再试试:

import logging
logging.basicConfig(level=logging.INFO)

  看到输出了:

    

  这就是logging的好处,它允许你指定记录信息的级别,有debuginfowarningerror等几个级别,当我们指定level=INFO时,logging.debug就不起作用了。同理,指定level=WARNING后,debuginfo就不起作用了。这样一来,你可以放心地输出不同级别的信息,也不用删除,最后统一控制输出哪个级别的信息。

  logging的另一个好处是通过简单的配置,一条语句可以同时输出到不同的地方,比如console和文件。

pdb

  第4种方式是启动Python的调试器pdb,让程序以单步方式运行,可以随时查看运行状态。我们先准备好程序:

s = ''
n = int(s)
print(10 / n)

  然后启动:

    

  以参数-m pdb启动后,pdb定位到下一步要执行的代码-> s = '0'。输入命令l来查看代码:

    

  输入命令n可以单步执行代码:

    

  任何时候都可以输入命令p 变量名来查看变量:

    

  输入命令q结束调试,退出程序:

(Pdb) q

  这种通过pdb在命令行调试的方法理论上是万能的,但实在是太麻烦了,如果有一千行代码,要运行到第999行得敲多少命令啊。还好,我们还有另一种调试方法。

  

pdb.set_trace()

  这个方法也是用pdb,但是不需要单步执行,我们只需要import pdb,然后,在可能出错的地方放一个pdb.set_trace(),就可以设置一个断点:

import pdb

s = ''
n = int(s)
pdb.set_trace() # 运行到这里会自动暂停
print(10 / n)

  运行代码,程序会自动在pdb.set_trace()暂停并进入pdb调试环境,可以用命令p查看变量,或者用命令c继续运行:

    

  这个方式比直接启动pdb单步调试效率要高很多,但也高不到哪去。

IDE

  如果要比较爽地设置断点、单步执行,就需要一个支持调试功能的IDE。目前比较好的Python IDE有PyCharm:

  http://www.jetbrains.com/pycharm/

  另外,Eclipse加上pydev插件也可以调试Python程序。

小结

  写程序最痛苦的事情莫过于调试,程序往往会以你意想不到的流程来运行,你期待执行的语句其实根本没有执行,这时候,就需要调试了。

  虽然用IDE调试起来比较方便,但是最后你会发现,logging才是终极武器

参考源码:

  do_assert.py:

 #python 调试   示例
#断言assert示例
#2016-8-31 20:25:15
#MengmengCoding
# -*- coding: utf-8 -*- def foo(s):
n=int(s)
assert n!=0,'n is zero!'
return 10/n def main():
foo('') main()

  do_logging.py:

 #python 调试   示例
#logging示例
#2016-8-31 20:31:56
#MengmengCoding
# -*- coding: utf-8 -*- import logging
logging.basicConfig(level=logging.INFO)
s=''
n=int(s)
logging.info('n=%d' %n)
print(10/n)

  do_pdb.py:

 #python 调试   示例
#pdb示例
#2016-8-31 20:44:55
#MengmengCoding
# -*- coding: utf-8 -*- import pdb s=''
n=int(s)
pdb.set_trace() #运行到这里会自动暂停
print(10/n)

  

  

python基础——调试的更多相关文章

  1. python基础===利用PyCharm进行Python远程调试(转)

    原文链接:利用PyCharm进行Python远程调试 背景描述 有时候Python应用的代码在本地开发环境运行十分正常,但是放到线上以后却出现了莫名其妙的异常,经过再三排查以后还是找不到问题原因,于是 ...

  2. python基础之错误、调试(异常处理)

    在程序运行过程中,总会遇到各种各样的错误. 有的错误是程序编写有问题造成的,比如本来应该输出整数结果输出了字符串,这种错误我们通常称之为bug,bug是必须修复的. 有的错误是用户输入造成的,比如让用 ...

  3. Python之路【第二篇】:Python基础

    参考链接:老师 BLOG : http://www.cnblogs.com/wupeiqi/articles/4906230.html 入门拾遗 一.作用域 只要变量在内存中就能被调用!但是(函数的栈 ...

  4. python基础——定制类

    python基础——定制类 看到类似__slots__这种形如__xxx__的变量或者函数名就要注意,这些在Python中是有特殊用途的. __slots__我们已经知道怎么用了,__len__()方 ...

  5. python基础——filter函数

    python基础——filter函数 Python内建的filter()函数用于过滤序列. 和map()类似,filter()也接收一个函数和一个序列.和map()不同的是,filter()把传入的函 ...

  6. Python基础教程【读书笔记】 - 2016/7/31

    希望通过博客园持续的更新,分享和记录Python基础知识到高级应用的点点滴滴! 第十波:第10章  充电时刻 Python语言的核心非常强大,同时还提供了更多值得一试的工具.Python的标准安装包括 ...

  7. 第一篇:python基础

    python基础   python基础 本节内容 python起源 python的发展史 为什么选择python3 第一个python程序 变量定义 表达式和运算符 用户输入 流程控制 判断 流程控制 ...

  8. Day1 - Python基础1 介绍、基本语法、流程控制

    Python之路,Day1 - Python基础1   本节内容 Python介绍 发展史 Python 2 or 3? 安装 Hello World程序 变量 用户输入 模块初识 .pyc是个什么鬼 ...

  9. Day1 Python基础学习

    一.编程语言分类 1.简介 机器语言:站在计算机的角度,说计算机能听懂的语言,那就是直接用二进制编程,直接操作硬件 汇编语言:站在计算机的角度,简写的英文标识符取代二进制去编写程序,本质仍然是直接操作 ...

随机推荐

  1. MongoDB的安全(五)

    MongoDB用户管理操作: MongoDB开启权限认证的方式有两种一种是auth形式,一种是keyfile形式 MongoDB创建用户: 1. 创建用户语法:在MongoDB2.6版本之后使用cre ...

  2. 基于SSL协议的双向认证 - 数字证书 [2]

    1.1    数字证书 1.1.1   概念理解 一种文件的名称,例如一个机构或人的签名,能够证明这个机构或人的真实性.简而言之数字证书是一种网络上证明持有者身份的文件,同时还包括有公钥.证书是由国际 ...

  3. 五款最佳Linux下载管理器推荐

    导读 新的Linux用户从Windows转换过来时面临的困难之一就是,找到一款优秀的下载管理器.如果你是或曾经是Windows用户,可能熟悉互联网下载管理器(IDM).下载加速器Plus(DAP)之类 ...

  4. 顺序栈的c++实现及利用其实现括号的匹配

    #include<iostream>#include<cassert>#include<cstring>#include<string>using na ...

  5. mysql的安装以及基本操作

    一.在Linux 下安装MySQL ubuntu 下可以直接使用apt-get . centos 下yum源有没有就不知道了. 1. sudo apt-get install mysql-server ...

  6. vSphere、Hyper-V与XenServer 你选哪个?

    vSphere.Hyper-V与XenServer 你选哪个? 当在VMware vSphere.Microsoft Hyper-V与Citrix Systems XenServer之间做出选择时,v ...

  7. Python判断当前用户是否是root

    import osif os.geteuid() != 0:print "This program must be run as root. Aborting."sys.exit( ...

  8. ubuntu add application to launcher

    eg. add sublime text to launcher so as to be found by launcher, docky, etc. add a file sudo gedit /u ...

  9. Wilson定理证明

    Wilson定理证明 就是那个\((p-1)! \equiv -1 \pmod{p}\),\(p\)是一个素数. Lemma A \(\mathbb{Z}_p\)可以去掉一个零元变成一个群. 即\(\ ...

  10. IntelliJ IDEA 常用快捷键列表及技巧大全

    IntelliJ Idea 常用快捷键列表 Alt+回车 导入包,自动修正Ctrl+N  查找类Ctrl+Shift+N 查找文件Ctrl+Alt+L  格式化代码Ctrl+Alt+O 优化导入的类和 ...