python在程序运行出现错误时时有相应的反应机制 ,我们可以针对不同的错误做出不同的响应
1 list1 = ['a','b','c'] 2 print(list1[4]) #>>>IndexError: list index out of range 3 a = {"name":"Jack", 4 "age":22} 5 print(a["sex"]) #KeyError: 'sex'
例子中分别指出了两个错误:IndexError和KeyError。如果我们想对程序中是否出现了这种错误,可以抓取出来。下面我们就针对这两种错误举例
1 list1 = ['a','b','c'] 2 a = {"name":"Jack", 3 "age":22} 4 try: 5 list1[2] 6 a["sex"] #这里是有错的! 7 except IndexError as e: 8 print("列表操作错误",e) 9 except KeyError as e: 10 print("没有这个key",e)
当try里的代码出现错误的话,通过except把错误获取
C:UsersAaronAnaconda3python.exe D:/python/week7/错误处理.py 没有这个key 'sex'
这样就会得到了,可是如果会有很多种错误的话,每种错误都加个except也太麻烦了!就可以这么写:
1 list1 = ['a','b','c'] 2 a = {"name":"Jack", 3 "age":22} 4 try: 5 list1[5] #这里是有错的! 6 a["sex"] #这里是有错的! 7 except (IndexError,KeyError) as e: 8 print("错误!",e)
但又出了个问题,用这种写法的话当出现错误,不能很好的显示错误的种类例子中两个条件都是错误的,只能显示成
C:UsersAaronAnaconda3python.exe D:/python/week7/错误处理.py
错误! list index out of range
所以这种方式是不推荐使用的!可是既然可以这么写,是不是有其他的作用呢?这时需要一个另外的用法——万能异常:Exception,可以把所有的错误抓取。这时候就可以做排除已知错误外的所有未知错误。
1 list1 = ['a','b','c'] 2 a = {"name":"Jack", 3 "age":22} 4 try: 5 list1[2] 6 a["name"] 7 open("没有这个文件.txt")#这里是有错的! 8 except IndexError as e: 9 print("列表操作错误",e) 10 except KeyError as e: 11 print("没有这个key",e) 12 except Exception as e: 13 print("未知错误",e)
在前面的错误类型都没有的话,可以显示最后的错误!
C:UsersAaronAnaconda3python.exe D:/python/week7/错误处理.py 未知错误 [Errno 2] No such file or directory: '没有这个文件.txt'
总而言之,一般的异常处理结构是这样的:
1 list1 = ['a','b','c'] 2 a = {"name":"Jack", 3 "age":22} 4 try: 5 list1[2] 6 a["name"] 7 open("没有这个文件.txt")#这里是有错的! 8 except (IndexError,KeyError) as e: 9 print("列表操作错误",e) 10 except KeyError as e: 11 print("没有这个key",e) 12 except Exception as e: 13 print("未知错误",e) 14 else: 15 print("一切正常") 16 finally: 17 print("无论是否发生异常,这里的代码都要执行")
我们现在看一看常用的异常代码
AttributeError 试图访问一个对象没有的属性,比如foo.x,但是foo没有属性x IOError 输入/输出异常;基本上是无法打开文件 ImportError 无法引入模块或包;基本上是路径问题或名称错误 IndentationError 语法错误(的子类) ;代码没有正确对齐 IndexError 下标索引超出序列边界,比如当x只有三个元素,却试图访问x[5] KeyError 试图访问字典里不存在的键 KeyboardInterrupt Ctrl+C被按下 NameError 使用一个还未被赋予对象的变量 SyntaxError Python代码非法,代码不能编译(个人认为这是语法错误,写错了) TypeError 传入对象类型与要求的不符合 UnboundLocalError 试图访问一个还未被设置的局部变量,基本上是由于另有一个同名的全局变量, 导致你以为正在访问它 ValueError 传入一个调用者不期望的值,即使值的类型是正确的
对了,还有一种异常处理在程序调试中可以用到:触发异常:
1 try: 2 raise KeyError 3 except KeyError as e: 4 print("没有这个Key",e)
在try中加入 raise,可以通过代码直接触发异常
最后,还有一种异常的用法:自定义异常
1 class concect_Error(Exception): 2 def __init__(self,msg): 3 self.msg = msg 4 try: 5 raise concect_Error("数据库连接失败") 6 except concect_Error as e: 7 print(e)
要注意的是,在定义错误的类中,一定要继承Exception的属性。自定义的类是属于Exception这个大类的!