Python的try... excep異常捕捉機制
異常:
異常即非正常狀態,在Python中使用異常對象來表示異常。若程序在編譯或運行過程中發生錯誤,程序的執行過程就會發生改變,拋出異常對象,程序流進入異常處理。如果異常對象沒有被處理或捕捉,程序就會執行回溯(Traceback)來終止程序。
一、沒有加入異常捕捉機制
test_list = [1, 2]
print(test_list[3])
執行之後,會在控制檯輸出:IndexError
錯誤, 意思是超過了列表的索引範圍
二、加入try … except 異常捕捉
1、已知錯誤類型 (例如下面已知列表索引錯誤類型IndexError
)
下面以一個列表索引的例子來講述 try... except的用法
1、異常類型起別名
import logging
logging.basicConfig(level=logging.INFO,
filename='Error.log',
format='%(asctime)s - %(message)s')
test_list = [1, 2]
try:
print(test_list[2])
except IndexError as e:
logging.error("索引越界:%s" % e)
我們知道捕捉的異常類型是IndexError
測試可以直接在except後面加上異常類型
在日誌中保存捕捉的異常信息,Error.log 中保存的異常信息如下:
2019-04-18 14:24:19,109 - 索引越界:list index out of range
2、異常類型不起別名
import logging
logging.basicConfig(level=logging.INFO,
filename='Error.log',
format='%(asctime)s - %(message)s')
test_list = [1, 2]
try:
print(test_list[2])
except IndexError:
logging.error("索引越界:%s" % IndexError)
在日誌中保存捕捉的異常信息,Error.log 中保存的異常信息如下:
2019-04-18 14:36:47,177 - 索引越界:<class 'IndexError'>
3、把異常的類型和錯誤信息都輸出
import logging
logging.basicConfig(level=logging.INFO,
filename='Error.log',
format='%(asctime)s - %(message)s')
test_list = [1, 2]
try:
print(test_list[2])
except IndexError as e:
logging.error("索引越界:%s" % IndexError) # 輸出錯誤的類型
logging.error("索引越界:%s" % e) # 輸出錯誤的信息
在日誌中保存捕捉的異常信息,Error.log 中保存的異常信息如下:
2019-04-18 14:39:11,863 - 索引越界:<class 'IndexError'>
2019-04-18 14:39:11,863 - 索引越界:list index out of range
2、未知異常的類型
有些異常類型可能我們在事先之前並不知道,應該步捕捉呢,此時可以用 Exception
代替未知的異常類型,也就是Exception 和 IndexError其實就是等價的啦,只是我們看代碼沒有明顯說明是什麼異常類型而已
舉例:
import logging
logging.basicConfig(level=logging.INFO,
filename='Error.log',
format='%(asctime)s - %(message)s')
test_list = [1, 2]
try:
print(test_list[2])
except Exception as e:
logging.error("索引越界:%s" % IndexError)
logging.error("索引越界:%s" % e)
在日誌中保存捕捉的異常信息,Error.log 中保存的異常信息如下:
2019-04-18 14:50:49,419 - 索引越界:<class 'IndexError'>
2019-04-18 14:50:49,419 - 索引越界:list index out of range
三、try … except … else … finally 使用
try:
except:
else
: 只有不發生異常纔會執行
finally
: 無論是否發生異常都會執行
import logging
logging.basicConfig(level=logging.INFO,
filename='Error.log',
format='%(asctime)s - %(message)s - %(module)s.py')
test_list = [1, 2]
try:
print(test_list[3])
except Exception as e:
logging.error("索引越界:%s" % IndexError)
logging.error("索引越界:%s" % e)
else:
logging.info("只有不發生異常纔會執行") # 程序不報錯纔會執行
finally:
logging.info("無論是否發生異常都會執行") # 程序報不報錯都會執行
print("捕捉到錯誤,這裏也是會執行的")
把異常的信息記錄到日誌中,之後下面的代碼還會繼續執行
在日誌中保存捕捉的異常信息,Error.log 中保存的異常信息如下:
2019-04-18 19:06:26,820 - 索引越界:<class 'IndexError'> - error_catch.py
2019-04-18 19:06:26,821 - 索引越界:list index out of range - error_catch.py
2019-04-18 19:06:26,821 - 無論是否發生異常都會執行 - error_catch.py
四、logging模塊調用異常捕捉方法,保存異常信息日誌
logging模塊,有兩個方法可以直接保存異常的日誌信息
- logging.error()
- logging.exception()
兩個方法的文檔:
def error(msg, *args, **kwargs):
"""
Log a message with severity 'ERROR' on the root logger. If the logger has
no handlers, call basicConfig() to add a console handler with a pre-defined
format.
"""
if len(root.handlers) == 0:
basicConfig()
root.error(msg, *args, **kwargs)
def exception(msg, *args, exc_info=True, **kwargs):
"""
Log a message with severity 'ERROR' on the root logger, with exception
information. If the logger has no handlers, basicConfig() is called to add
a console handler with a pre-defined format.
"""
error(msg, *args, exc_info=exc_info, **kwargs)
2、例子
import logging
logging.basicConfig(level=logging.INFO,
filename='Error.log',
format='%(asctime)s - %(message)s - %(module)s.py')
test_list = [1, 2]
try:
print(test_list[2])
except Exception as e:
logging.error(e)
logging.info("----------------------------------------")
logging.exception(e)
print("捕捉到錯誤,這裏也是會執行的")
在日誌中保存捕捉的異常信息,Error.log 中保存的異常信息如下:
從日誌內容可以看出:
logging.error()
: 輸出的是簡短的異常信息logging.exception()
:輸出的是詳細的異常信息
五、常用的異常類型表
異常 | 描述 |
---|---|
BaseException | 所有異常的基類 |
SystemExit | 解釋器請求退出 |
KeyboardInterrupt | 用戶中斷執行(通常是輸入^C) |
Exception | 常規錯誤的基類 |
StopIteration | 迭代器沒有更多的值 |
GeneratorExit | 生成器(generator)發生異常來通知退出 |
StandardError | 所有的內建標準異常的基類 |
ArithmeticError | 所有數值計算錯誤的基類 |
FloatingPointError | 浮點計算錯誤 |
OverflowError | 數值運算超出最大限制 |
ZeroDivisionError | 除(或取模)零 (所有數據類型) |
AssertionError | 斷言語句失敗 |
AttributeError | 對象沒有這個屬性 |
EOFError | 沒有內建輸入,到達EOF 標記 |
EnvironmentError | 操作系統錯誤的基類 |
IOError | 輸入/輸出操作失敗 |
OSError | 操作系統錯誤 |
WindowsError | 系統調用失敗 |
ImportError | 導入模塊/對象失敗 |
LookupError | 無效數據查詢的基類 |
IndexError | 序列中沒有此索引(index) |
KeyError | 映射中沒有這個鍵 |
MemoryError | 內存溢出錯誤(對於Python 解釋器不是致命的) |
NameError | 未聲明/初始化對象 (沒有屬性) |
UnboundLocalError | 訪問未初始化的本地變量 |
ReferenceError | 弱引用(Weak reference)試圖訪問已經垃圾回收了的對象 |
RuntimeError | 一般的運行時錯誤 |
NotImplementedError | 尚未實現的方法 |
SyntaxError | Python 語法錯誤 |
IndentationError | 縮進錯誤 |
TabError | Tab 和空格混用 |
SystemError | 一般的解釋器系統錯誤 |
TypeError | 對類型無效的操作 |
ValueError | 傳入無效的參數 |
UnicodeError | Unicode 相關的錯誤 |
UnicodeDecodeError | Unicode 解碼時的錯誤 |
UnicodeEncodeError | Unicode 編碼時錯誤 |
UnicodeTranslateError | Unicode 轉換時錯誤 |
Warning | 警告的基類 |
DeprecationWarning | 關於被棄用的特徵的警告 |
FutureWarning | 關於構造將來語義會有改變的警告 |
OverflowWarning | 舊的關於自動提升爲長整型(long)的警告 |
PendingDeprecationWarning | 關於特性將會被廢棄的警告 |
RuntimeWarning | 可疑的運行時行爲(runtime behavior)的警告 |
SyntaxWarning | 可疑的語法的警告 |
UserWarning | 用戶代碼生成的警告 |
Exception類:是通用異常基類下列異常類均繼承於Exception類,Python解析器會自動將通用異常類型名稱放在內建命名空間中,所以當使用通用異常類型時,不需要import exceptions模塊。
參考:
1、https://blog.csdn.net/zong596568821xp/article/details/78180229
2、http://www.runoob.com/python/python-exceptions.html