异常
错误处理:
1、python错误处理机制:try...exception...finally...
若认为某些代码可能会出错时,就可以用try来运行这段代码,如果执行出错,则后续代码不会继续执行,而是直接跳转至错误处理代码即except语句块;执行完except后,如果有finally语句块,则执行finally语句块,至此,执行完毕
此外,如果没有错误发生,可以在except语句块后面加一个else,当没有错误发生时,会自动执行else语句
python的错误其实也是class,所有错误类型都继承自BaseException,所以在使用except时需要注意,它不但捕获该类型的错误,还把子类也‘一网打尽’
try: foo() except StandardError, e: print 'StandardError' except ValueError, e: print 'ValueError'
第二个except永远也捕获不到ValueError,因为ValueError是StandardError的子类,如果有,也被第一个except给捕获了
BaseException
+-- SystemExit
+-- KeyboardInterrupt
+-- GeneratorExit
+-- Exception
+-- StopIteration
+-- StandardError
| +-- BufferError
| +-- ArithmeticError
| | +-- FloatingPointError
| | +-- OverflowError
| | +-- ZeroDivisionError :除数为0,再用除法操作时,第二个参数为0时引发了该错误
| +-- AssertionError :断言失败,assert语句本身会抛出该错误
| +-- AttributeError :试图访问一个对象没有的属性,比如foo.x,但是foo没有属性x
| +-- EnvironmentError
| | +-- IOError :输入/输出异常(基本上是无法打开文件)
| | +-- OSError
| | +-- WindowsError (Windows)
| | +-- VMSError (VMS)
| +-- EOFError
| +-- ImportError :无法引入模块或包,基本上是路径问题或名称错误
| +-- LookupError
| | +-- IndexError :下标索引超出序列边界
| | +-- KeyError :试图访问不存在的键
| +-- MemoryError
| +-- NameError :使用一个还未被赋予对象的变量
| | +-- UnboundLocalError :试图访问一个还未被设置的局部变量
| +-- ReferenceError
| +-- RuntimeError
| | +-- NotImplementedError
| +-- SyntaxError :python代码非法,代码不能编译
| | +-- IndentationError :语法错误的子类,代码没有正确对齐
| | +-- TabError
| +-- SystemError
| +-- TypeError :传入对象类型与要求的不符合
| +-- ValueError :传入一个调用者不期望的值,即使值的类型是正确的
| +-- UnicodeError
| +-- UnicodeDecodeError
| +-- UnicodeEncodeError
| +-- UnicodeTranslateError
+-- Warning
+-- DeprecationWarning
+-- PendingDeprecationWarning
+-- RuntimeWarning
+-- SyntaxWarning
+-- UserWarning
+-- FutureWarning
+-- ImportWarning
+-- UnicodeWarning
+-- BytesWarning
2、抛出错误
因为错误是class,捕获一个错误就是捕获到该class的一个实例。因此,错误并不是凭空产生的,而是有意创建并抛出的。python的内置函数会抛出很多类型的错误,我们编写的函数也可以抛出错误
如果要抛出错误,首先根据需求,可以定义一个错误的class,选择好继承关系,然后用 raise 语句抛出一个错误的实例:尽量使用python内置的错误类型
class FooError(StandardError):
pass
def foo(s):
n=int(s)
if n==0:
raise FooError('invalid value : %s' %s)
return 10/n
-------------------------------------------------------------------------------------------------------------------------------
调试:
1、用 print 把可能有问题的变量打印出来看看:坏处还得删除,运行结果会包含很多垃圾信息
def foo(s):
n=int(s)
print '>>> n=%d' % n
return 10/n
def main():
foo('0')
main()
输出:
>>> n=0
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 2, in main
File "<stdin>", line 4, in foo
ZeroDivisionError: integer division or modulo by zero
2、断言:凡是用print来辅助的地方,都可以用断言(assert)来替代
def foo(s):
n=int(s)
assert n != 0,'n is zero!' assert语句后跟任何合法的python表达式,若表达式为True,则assert不做任何事情;若表达式为False,则会抛出AssertionError
return 10/n
def main():
foo('0')
main()
输出:
>>> main()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 2, in main
File "<stdin>", line 3, in foo
AssertionError: n is zero!
3、logging好处,允许指定记录信息的级别,有debug、info、warning、error几个级别,当我们指定lenvel=INFO时,logging.debug就不起作用了

浙公网安备 33010602011771号