Python 有兩種錯誤很容易辨認:語法錯誤和例外(本文將重點介紹python的例外),
python語法錯誤:
Python 的語法錯誤或者稱之為決議錯,是初學者經常碰到的;
>>>while True print('Hello world') File "<stdin>", line 1, in ? while True print('Hello world') ^ SyntaxError: invalid syntax
函式 print() 被檢查到有錯誤,是它前面缺少了一個冒號 : ,語法分析器指出了出錯的一行,并且在最先找到的錯誤的位置標記了一個小小的箭頭,
python例外:
即便 Python 程式的語法是正確的,在運行它的時候,也有可能發生錯誤,運行期檢測到的錯誤被稱為例外,例外即是一個事件,該事件會在程式執行程序中發生,影響了程式的正常執行;一般情況下,在Python無法正常處理程式時就會發生一個例外;例外是Python物件,表示一個錯誤;當Python腳本發生例外時我們需要捕獲處理它,否則程式會終止執行,
>>>10 * (1/0) # 0 不能作為除數,觸發例外 Traceback (most recent call last): File "<stdin>", line 1, in ? ZeroDivisionError: division by zero
>>> 4 + spam*3 # spam 未定義,觸發例外 Traceback (most recent call last): File "<stdin>", line 1, in ? NameError: name 'spam' is not defined
>>> '2' + 2 # int 不能與 str 相加,觸發例外 Traceback (most recent call last): File "<stdin>", line 1, in ? TypeError: Can't convert 'int' object to str implicitly
例外以不同的型別出現,這些型別都作為資訊的一部分列印出來: 例子中的型別有 ZeroDivisionError,NameError 和 TypeError,錯誤資訊的前面部分顯示了例外發生的背景關系,并以呼叫堆疊的形式顯示具體資訊,
python例外的處理:
python提供了兩個非常重要的功能來處理python程式在運行中出現的例外和錯誤,你可以使用該功能來除錯python程式,例外處理和斷言(Assertions),
例外處理涉及的5個關鍵字:
try:理解它是掃描器,將可能出現例外的代碼放入其中;如果在執行的程序中出現例外物件了,掃描器會立即察覺到此例外物件,但是它沒有處理它的能力,所以會將例外物件給到except(捕獲器)進行處理,
except:理解它是捕獲器,后面可以定義例外型別,并且和as關鍵字配合使用;定義多個except是合法的,但是它的執行順序是有由上往下,一旦匹配上某個except,之后的就不執行了;匹配成功就理解將例外物件捕獲住并且kill,順便會執行except內部的代碼,(注意:except不能捕獲處理類似于語法錯誤這種情況)
finally:將一定需要被執行的代碼定義其中,【記住】:finally一定會被執行(核心);使用場景:像關閉檔案、斷開資料庫連接等行為都可以放入到finally中,
else:位置在finally前,except后;效果/作用類似于回圈;沒有例外物件出現,else就會被執行,反之不會被執行,
raise:手動拋出一個例外型別的物件,定義:raise 例外型別(msg),
定義格式:
格式一: 多個except陳述句并列存在,每個except包含一種型別,如果它們之間沒有子父類的關系(互斥),那么誰上誰下無所謂, 如果它們之間存在子父類的關系(包含),那么小的在上,大的在下,
try: 陳述句塊1 except 例外型別1 as e: 陳述句塊2 except 例外型別2 as e: 陳述句塊3 except 例外型別3 as e: 陳述句塊4 finally: 陳述句塊5
格式二:一個except具備多個捕獲能力(捕獲多種不同型別例外物件),
try: 陳述句塊1 except 例外型別1 as e: 陳述句塊2 except 例外型別2 as e: 陳述句塊3 except 例外型別3 as e: 陳述句塊4 except (例外型別4,例外型別5,...,例外型別m) as e: finally: 陳述句塊5
格式三:Exception是所有例外型別的父型別,它都是定義在最后一個except的位置,
try: 陳述句塊1 except 例外型別1 as e: 陳述句塊2 except 例外型別2 as e: 陳述句塊3 except 例外型別3 as e: 陳述句塊4 except (例外型別4,例外型別5,...,例外型別m) as e: 陳述句塊5 except Exception as e: 陳述句塊6 finally: 陳述句塊7
格式四: 【Exception的簡化版使用】:如果定義了except,那么它必須是最后一個except,它可以理解為是Exception的簡化形式
try: 陳述句塊1 except 例外型別1 as e: 陳述句塊2 except 例外型別2 as e: 陳述句塊3 except 例外型別3 as e: 陳述句塊4 except (例外型別4,例外型別5,...,例外型別m) as e: 陳述句塊5 except: 陳述句塊6 finally: 陳述句塊7
代碼演示自動拋出例外物件:
2 3 def div(a,b): 4 print(a / b) 5 6 div(10,0) 7 8 # 演示例外處理的方式一:try ... except ... 9 try: 10 print(10/0) 11 except ZeroDivisionError as e: 12 print(e) 13 14 try: 15 print("abc"+123) 16 except TypeError as e: 17 print(e) 18 19 try: 20 print(a) 21 except NameError as e: 22 print(e) 23 24 try: 25 lt = [1,2,3,4,5] 26 print(lt[5]) 27 except IndexError as e: 28 print(e) 29 30 try: 31 fr = open(r'C:\Users\Administrator\Desktop\kaifanglist1.txt','r',encoding='utf-8') 32 print(fr.read()) 33 fr.close() 34 except FileNotFoundError as e: 35 print(e) 36 37 except(ZeroDivisionError,TypeError,NameError,IndexError,FileNotFoundError) as e: 38 print('我能捕獲5種型別的例外物件...') 39 40 except Exception as e: 41 print('我是所有例外型別的父型別,我能解決所有的例外型別物件...') 42 43 except: 44 print('我是Exception的簡化形式,我只能出現在最后一個except的位置...')
代碼演示finally陳述句的使用:將一定要被執行的代碼定義在finally中,不管之前的代碼怎么樣(例外是否被解決),finally一定會被執行,在后期的學習和開發中,我們將關閉檔案、關閉資料庫連接等操作都定finally中,
1 try: 2 fr = open(r'C:\Users\Administrator\Desktop\a.txt','r') # 檔案能打開 3 print(fr.read()) 4 print(10 / 0) 5 # fr.close() # 因為關閉檔案操作是一定要被執行的 但是在try里面也有可能存在風險性,當print(10 / 0)行不了,則無法執行close操作,所以關閉檔案需要放在finally陳述句當中
6 except: 7 print('解決例外') 8 finally: 9 print('我是finally,我一定會被執行...') 10 fr.close() 11 12 13 # 但是如果一開始就是一個打不開的檔案,則也沒有辦法關閉檔案 14 fr = 0 15 try: 16 fr = open(r'C:\Users\Administrator\Desktop\a111.txt','r') # 沒有此檔案名 (檔案存在則fr不為None值) 17 print(fr.read()) 18 except: 19 print('解決例外') 20 finally: 21 print('我是finally,我一定會被執行...') 22 if fr: # fr為None值則if為False,否則為True,執行以下指令(為了安全性) 23 fr.close()
finally案例演示二(進一步理解):
1 # Finally案例:分別輸出了哪些內容,回傳值是多少 2 3 def func(): 4 try: 5 print('我是try...') 6 print(10 / 2) 7 return 1 #執行此步 則函式就結束了,又因為finally一定要被執行,所以return 1不會被執行,直接調到finally 8 except: 9 print('我是except...') 10 return 2 11 finally: 12 print('我是finally...') 13 return 3 14 15 num = func() 16 print(num) 17 '''結果得到是 18 我是try... 19 5.0 20 我是finally... 21 3''' 22 23 # 如果題目改為如下,則 24 def func(): 25 try: 26 print('我是try...') 27 print(10 / 0) 28 return 1 29 except: 30 print('我是except...') 31 return 2 #執行此步 則函式就結束了,又因為finally一定要被執行,所以return 2不會被執行,直接調到finally 32 finally: 33 print('我是finally...') 34 return 3 35 36 num = func() 37 print(num) 38 '''結果得到是 39 我是try... 40 我是except... 41 我是finally... 42 3''' 43
【補充】with open...操作:不需要程式員人為的去書寫 close() 函式
1 With open(r'C:\Users\Administrator\Desktop\a.txt','r')as fr: 2 print(fr.read())
解決例外也是一樣:
1 try: 2 with open(r'C:\Users\Administrator\Desktop\a.txt','r') as fr: 3 print(fr.read()) 4 except: 5 print('解決例外...')
代碼演示else陳述句和例外處理機制配合使用:如果try中沒有出現例外物件,那么else陳述句就一定會被執行,如果try中出現了例外物件,就算被處理了,else還是不會被執行,
1 try: 2 print('我是try...') 3 print(10 / 0) 4 except Exception as e: 5 print('我是except...') 6 else: 7 print('我是else...') 8 finally: 9 print('我是finally...')
10 #得到 11 我是try... 12 我是except... 13 我是finally... 14 15 #如果把print(10 / 0) 改為print(10 / 2) 16 17 #得到 18 我是try... 19 5.0 20 我是else... 21 我是finally...
代碼演示raise的使用:(手動拋出例外物件)
1 age = 18 2 if age < 0 or age > 130: 3 try: 4 raise Exception('年齡有問題...') 5 except: 6 print('年齡不合法...正在處理') 7 pass 8 else: 9 print('年齡為:%d' %age) 10 print('能走嗎?') 11 12 #得到結果為 13 年齡為:18 14 能走嗎? 15 16 #如果第一行是age=-18 17 #得到結果為 18 年齡不合法...正在處理 19 能走嗎?
1 # 演示例外處理的方式二:不斷往上級傳遞例外物件,回避問題的方式 2 3 def m1(): 4 print('我是m1...') 5 print(10 / 0) 6 7 def m2(): 8 print('我是m2...') 9 # try: 10 m1() 11 # except: 12 # pass 13 14 def m3(): 15 print('我是m3...') 16 try: 17 m2() 18 except: 19 pass 20 21 m3() 22 #得到結果 23 我是m3... 24 我是m2... 25 我是m1...
python標準例外總結:
| 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 | 用戶代碼生成的警告 |
【注意事項】:
1).try...finally這種格式是合法的,但是它喪失了解決例外物件的能力(所以不會使用)
2).else陳述句必須配合except使用,出現位置一定是在最后一個except的后面
3).常見的運行時例外型別:ZeroDivisionError:分母為0的例外;TypeError:型別有誤的例外; NameError:沒有定義就使用的例外;IndexError:下標越界的異;FileNotFoundError:檔案找不到的例外;...
4).with open ... as ...陳述句可以優化原始的open操作!體現:它不需要手動close()檔案物件
總結:學習例外物件簡單歸納為5個關鍵字:try except finally else raise
python的assert(斷言):
Python的assert(斷言)用于判斷一個運算式,在運算式條件為 false 的時候觸發例外,斷言可以在條件不滿足程式運行的情況下直接回傳錯誤,而不必等待程式運行后出現崩潰的情況,例如我們的代碼只能在 Linux 系統下運行,可以先判斷當前系統是否符合條件,
語法格式如下:assert expression
等價于:
if not expression:
raise AssertionError
assert 后面也可以緊跟引數: assert expression [, arguments]
等價于:
if not expression:
raise AssertionError(arguments)
代碼演示assert示例:
1 >>> assert True # 條件為 true 正常執行 2 >>> assert False # 條件為 false 觸發例外 3 Traceback (most recent call last): 4 File "<stdin>", line 1, in <module> 5 AssertionError 6 7 >>> assert 1==1 # 條件為 true 正常執行 8 >>> assert 1==2 # 條件為 false 觸發例外 9 Traceback (most recent call last): 10 File "<stdin>", line 1, in <module> 11 AssertionError 12 13 >>> assert 1==2, '1 不等于 2' 14 Traceback (most recent call last): 15 File "<stdin>", line 1, in <module> 16 AssertionError: 1 不等于 2 17 18 19 # 判斷當前系統是否為 Linux,如果不滿足條件則直接觸發例外,不必執行接下來的代碼: 20 import sys 21 assert ('linux' in sys.platform), "該代碼只能在 Linux 下執行" 22 # 接下來要執行的代碼
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/188629.html
標籤:Python
下一篇:while單回圈練習
