----------------常见的Python异常----------------
异常 描 述
AssertionError assert语句失败
AttributeError 试图访问一个对象没有的属性
IOError 输入输出异常,基本是无法打开文件
ImportError 无法引入模块或者包,基本是路径问题
IndentationError 语法错误,代码没有正确的对齐
IndexError 下标索引超出序列边界
KeyError 试图访问你字典里不存在的键
KeyboardInterrupt ctrl+C被按下
NameError 尝试访问一个没有申明的变量
SyntaxError python代码逻辑语法出错
TypeError 传入的对象类型与要求不符
UnboundLocalError 试图访问一个还未设置的全局变量,基本上是由于另有一个同名的全局变量,导致你以为在访问
ValueError 传入一个不被期望的值,即使类型正确
----------------异常的处理----------------
(1)基础
try/except/else(可选):捕捉由代码中的异常并恢复,匹配except里面的错误,并执行except中定义的代码,后继续执行程序
(发生异常后,由except捕捉到异常后,不会中断程序,继续执行try语句后面的程序)
try首行底下的代码块代表此语句的主要动作:试着执行的程序代码。
except分句定义try代码块内引发的异常处理器,而else分句(如果有)则是提供没有发生异常时候要执行的处理器。
try/finally:无论异常是否发生,都执行清理行为 (发生异常时程序会中断程序,只不过会执行finally后的代码)
raise:手动在代码中接触发异常。
assert:有条件地在程序代码中触发异常。 assert几乎都是用来收集用户定义的约束条件。
with/as:在Python2.6和后续版本中实现环境管理器。
注:finally可以和except和else分句出现在相同的try语句内。
except捕捉到对应的异常才执行。else没有捕捉到异常才执行。
(2)try语句分句形式
分句形式 说明
except: 捕捉所有(其他)异常类型
except name: 只捕捉特定的异常
except name,value: 捕捉所有的异常和其额外的数据(或实例)
except (name1,name2) 捕捉任何列出的异常
except (name1,name2),value: 捕捉任何列出的异常,并取得其额外数据
else: 如果没有引发异常,就运行
finally: 总是会运行此代码块,无论是否发生异常
空的except分句会捕捉任何程序执行时所引发的而未被捕捉到的异常。要取得发生的实际异常,可以从内置的sys模块取出sys.exc_info函数的调用结果。
这会返回一个元组,而元组之前两个元素会自动包含当前异常的名称,以及相关的额外数据(如果有)。
就基于类的异常而言,这两个元素分别对应的是异常的类以及引发类的实例。
sys.exc_info结果是获得最近引发的异常更好的方式。如果没有处理器正在处理,就返回包含了三个None值的元组。否则,将会返回(type,value和traceback)
*type是正在处理的异常的异常类型(一个基于类的异常的类对象)
*value是异常参数(它的关联值或raise的第二个参数,如果异常类型为类对象,就一定是类实例)
*traceback是一个traceback对象,代表异常最初发生时所调用的堆栈。
例:
try:
main-action:
except Exception1:
hander1
except Exception2:
hander2
...
else:
else-block
finally:
finally-block
这语句中main-action代码会先执行。如果该程序代码(main-action)引发异常,那么except代码块都会逐一测试,寻找与抛出的异常相符的语句。
如果引发异常的是Exception1则会执行hander1代码块,如果引发异常的是Exception2,则会执行hander2代码块。以此类推。
如果没有引发异常,将会执行else-block代码块。无论前面发生什么,当main-action代码块完成时。finally-block都会执行。
(3)raise语句
要故意触发异常,可以使用raise语句。
raise语句组成是:raise关键字,后面跟着要引发的异常名称(选用),以及一个可选的额外的数据项,后可随着异常传递。
raise
raise ,
(4)assert语句
assert可以有条件地在程序代码中触发异常,可以认为是有条件的raise。
注意:assert几乎都是用来收集用户定义的约束条件,而不是捕捉内在的程序设计错误。因为Python会自动收集程序的设计错误,
通常没有必要写assert去捕捉超出索引值,类型不匹配以及除数为0之类的事。
assert ,
例:
>>> def f(x):
... assert x>0,'x must be great zerot'
... return x**2
(5)with语句
标准化的 try-except和try-finally 的用法是保证资源的分配和回收,比如文件(数据、日志、数据库等等)、线程资源、数据库连接等,但它们书写起来却不够优雅。
with语句的目的在于从流程图中把try、except、 finally关键字和资源分配、释放相关代码统统去掉。
例:
>>>with open('/etc/passwd') as f:
for line in f:
print(line)
注意:with语句仅能工作于支持上下文管理协议(context management protocol)的对象。
目前支持该协议的对象有:
file
decimal.Context
thread.LockType
threading.Lock
threading.RLock
threading.Condition
threading.Semaphore
threading.BoundedSemaphore