處理錯誤
- 由于出現(xiàn)錯誤而使某些操作沒有完成,程序應該:返回到一種安全狀態(tài),并能夠讓用戶執(zhí)行一些其他的命令,或者允許用戶保存所有操作的結(jié)果,并以妥善的方式終止程序。
- 異常對象都是派生于Throwable類的一個實例
- Error類層次結(jié)構(gòu)描述了Java運行時系統(tǒng)的內(nèi)部錯誤和資源耗盡錯誤。應用程序不應該拋出這種類型的錯誤。
- Exception層次結(jié)構(gòu)又分解為兩個分支:一個分支派生于RuntimeException;另一個分支包含其他異常。劃分兩個分支的規(guī)則是:由程序錯誤導致的異常屬于RuntimeException,如錯誤的類型轉(zhuǎn)換,數(shù)組訪問越界,訪問null指針;而程序本身沒有問題,但由于像IO錯誤這類問題導致的錯誤屬于其他異常。
- 如果出現(xiàn)RuntimeException異常,那么一定是你的問題。
- Java語言規(guī)范將派生于Error類或RuntimeException類的所有異常稱為非受查異常unchecked,所有其他的異常稱為受查異常。編譯器將核查是否為所有的受查異常提供了異常處理器
- 對于那些可能被他人使用的Java方法,應該根據(jù)異常規(guī)范Exception specification,在方法的首部聲明這個方法可能拋出的異常。
- 捕獲異常:如果在try語句塊中的任何代碼拋出了一個在catch子句中說明的異常類,那么1.程序?qū)⑻^try語句塊的其余代碼2.程序?qū)?zhí)行catch子句中的處理器代碼。
- 能處理的異常用try/catch,不能處理的異常throws拋出給調(diào)用者
- 使用getMessage()可以得到異常對象的信息,getClass().getName()可以得到異常對象的實際類型
- 在一個try語句中可以捕獲多個異常類型,并對不同類型的異常做出不同的處理。同一個catch子句中可以捕獲多個異常類型(使用| 分隔,只有在當捕獲的異常類型彼此之間不存在子類關系時才需要這個特性)
- 可以在catch子句中再次拋出異常 throw new ...Exception(...);
- 不管是否有異常被捕獲,finally子句中的代碼都被執(zhí)行
- try語句可以只有finally語句,而沒有catch語句
- 建議強烈耦合try/catch和try/finally語句
- 帶資源的try語句(try-with-resources)
使用異常機制的技巧
- 異常處理不能代替簡單的測試;使用異常的基本規(guī)則是:只在異常情況下使用異常機制。
- 不要過分地細化異常
- 利用異常層次結(jié)構(gòu)
- 不要壓制異常
- 在檢測錯誤時,“苛刻”要比放任更好
- 不要羞于傳遞異常(早拋出,晚捕獲)
使用斷言
- assert 條件:和assert 條件:表達式;都會對條件進行檢測,如果結(jié)果為false,則拋出一個AssertionError異常。第二種形式中,表達式將傳入AssertionError的構(gòu)造器,并轉(zhuǎn)換成一個消息字符串
- 使用斷言的情況:斷言失敗是致命的,不可恢復的錯誤;斷言檢查只用于開發(fā)和測試階段。
- 斷言是一種測試和調(diào)試階段所使用的戰(zhàn)術(shù)性工具。
記錄日志
- 日志記錄是一種在程序的整個生命周期都可以使用的策略性工具。
- 日志記錄API的優(yōu)點