Python常見異常的處理方式淺析
一、引言
有一定 Python 編程經(jīng)驗的人估計十有八九使用過異常,異常對于程序的健壯性是毋庸置疑的。
二、使用異常對數(shù)據(jù)進行初始化
在某些條件下,需要進行數(shù)據(jù)初始化,但數(shù)據(jù)不能提前確認,這個時候就可以結(jié)合異常的使用來判斷是否需要進行初始化。下面的代碼中的函數(shù) listDataStatics 用于統(tǒng)計列表中每個元素的出現(xiàn)個數(shù),處理時循環(huán)遍歷列表,對列表中已經(jīng)存在的元素計數(shù)器加 1,否則如果是鍵值不存在異常則進行數(shù)據(jù)初始化:
def listDataStatics(infList): dataInf = {} for l in infList: try: dataInf[l] += 1 except KeyError as e: dataInf[l] =1 return dataInf
當然上述過程也可以用列表的 index 等方法來實現(xiàn),但個人認為這種方式最簡單。
三、使用異常實現(xiàn)重處理
某些異常需要進行重處理,如出現(xiàn)網(wǎng)絡(luò)連接斷開時需要在網(wǎng)絡(luò)正常后重新訪問網(wǎng)絡(luò),下面是一個案例。
import urllib,time def getHtmlPage(url): while True: try: req = urllib.request.Request(url=url) text = urllib.request.urlopen(req).read().decode() except ConnectionError: print("ConnectionError:network has disconnected") time.sleep(3) continue except Exception as e: err = str(e) if err.find('getaddrinfo failed')>=0: print("getaddrinfo failed:network has disconnected") time.sleep(3) continue else: return '' else:return text
四、使用異常應(yīng)對多種潛在情況
在使用 Moviepy1.03 通過 VideoFileClip 執(zhí)行報 UnicodeDecodeError 錯,發(fā)現(xiàn)是少數(shù)視頻有問題,從報錯信息看是 Moviepy 的 ffmpeg_reader.py 模塊有個如下代碼:infos = error.decode(‘utf8’)
解碼出現(xiàn)問題,將其改為:infos = error.decode(‘ANSI’)
順利解決,但解決后用來加載其他視頻文件又報錯,后來將代碼改成如下方式:
try: infos = error.decode('utf8') except Exception as e: infos = error.decode('ANSI')
五、獲取異常詳細信息
Python 自己拋出的異常會有詳細的異常信息,包括異常類型、錯誤內(nèi)容、程序代碼位置及相關(guān)函數(shù)調(diào)用棧信息,但異常捕獲后這些錯誤信息默認就消失了,為了實現(xiàn)提供與 Python 相同的異常信息,需要異常捕獲程序進行處理:
通過類似except Exception as e
捕獲異常后,打印 e 的內(nèi)容(也可打印 e.errno、e.strerror)可以提供異常的類型及異常的錯誤信息說明;
采用 traceback 模塊的 print_exc 查看異常對應(yīng)程序代碼位置及相關(guān)函數(shù)調(diào)用棧信息發(fā)生異常時,Python 保留引發(fā)異常程序的當前狀態(tài),并可通過 traceback 跟蹤異常發(fā)生時與函數(shù)調(diào)用堆棧有關(guān)的信息。程序調(diào)用每個函數(shù)時,Python 會在“函數(shù)調(diào)用堆棧”的起始處插入函數(shù)名。一旦異常被引發(fā),Python 會搜索異常處理程序,如果當前函數(shù)中沒有異常處理程序,當前函數(shù)會終止執(zhí)行,Python 會搜索當前函數(shù)的調(diào)用函數(shù),并以此類推,直到發(fā)現(xiàn)匹配的異常處理程序,或者 Python 抵達主程序為止。這一查找合適的異常處理程序的過程就稱為“堆棧輾轉(zhuǎn)開解”(StackUnwinding)。
下面代碼在訪問網(wǎng)站遇到異常時,打印詳細的異常錯誤信息及代碼位置:
import urllib,traceback def getHtmlPage(url): try: req = urllib.request.Request(url=url) text = urllib.request.urlopen(req).read().decode() except Exception as e: print(f"訪問網(wǎng)站獲取推薦文章失敗,當前url={url},異常原因:\n{e}\n" + '\n' + traceback.format_exc() ) return '' else:return text
六、人工觸發(fā)異常
除了程序自動引發(fā)的異常外,也可以通過 raise 函數(shù)主動拋出異常,一般用在程序主動檢查發(fā)現(xiàn)錯誤的情況,避免錯誤擴散。下面這段代碼檢查列表 infList 中的元素是否為列表,如果不是列表則拋出異常:
for row in infList: if not isinstance(row,list): raise ValueError("checkAndRepairListData實參不滿足第一個參數(shù)為二維列表的要求!\n"+traceback.format_exc())
可以看到,使用 raise 拋出異常時,需要提供異常類型和異常信息,并在此時也可以獲取程序的代碼位置及函數(shù)堆棧信息。
七、異常嵌套
異常允許嵌套,包括在一個 try...except 語句的 try 和 except 之間嵌入另一個 try...except 語句,也可以在異常處理語句、else、finally 子句中再嵌套 try...except 語句,在此就不舉例介紹了。
小結(jié)
本文介紹了 Python 異常用于數(shù)據(jù)初始化、業(yè)務(wù)重處理、多情況處理的三種應(yīng)用方式,以及獲取異常詳細信息、人工觸發(fā)異常及異常嵌套等與異常相關(guān)的知識
到此這篇關(guān)于Python常見異常的處理方式淺析的文章就介紹到這了,更多相關(guān)Python異常處理內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Python?Matplotlib通過plt.subplots創(chuàng)建子繪圖
這篇文章主要介紹了Python?Matplotlib通過plt.subplots創(chuàng)建子繪圖,plt.subplots調(diào)用后將會產(chǎn)生一個圖表和默認網(wǎng)格,與此同時提供一個合理的控制策略布局子繪圖,更多相關(guān)需要的朋友可以參考下面文章內(nèi)容2022-07-07selenium學(xué)習教程之定位以及切換frame(iframe)
這篇文章主要給大家介紹了關(guān)于selenium學(xué)習教程之定位以及切換frame(iframe)的相關(guān)資料,文中通過示例代碼介紹的非常詳細,對大家的學(xué)習或者工作具有一定的參考學(xué)習價值,需要的朋友們下面隨著小編來一起學(xué)習學(xué)習吧2021-01-01python Requsets下載開源網(wǎng)站的代碼(帶索引 數(shù)據(jù))
這篇文章主要介紹了python Requsets下載開源網(wǎng)站的代碼(帶索引 數(shù)據(jù)),本文通過實例代碼給大家介紹的非常詳細,對大家的學(xué)習或工作具有一定的參考借鑒價值,需要的朋友可以參考下2021-04-04Django使用httpresponse返回用戶頭像實例代碼
這篇文章主要介紹了Django使用httpresponse返回用戶頭像實例代碼2018-01-01Python函數(shù)參數(shù)分類使用與新特性詳細分析講解
在聲明函數(shù)的時候,一般會根據(jù)函數(shù)所要實現(xiàn)的功能來決定函數(shù)是否需要參數(shù)。在多數(shù)情況下,我們聲明的函數(shù)都會使用到參數(shù),這篇文章主要介紹了Python函數(shù)參數(shù)2023-01-01