1. 程式人生 > >Effective Java讀書筆記(第9章-異常)

Effective Java讀書筆記(第9章-異常)

     第9章  異常

     第57條:只針對異常的情況才使用異常

     設計良好的API不應該強迫它的客戶端為了正常的控制流而使用異常。異常是為了在異常情況下使用而設計的,不要將它們用於普通的控制流,也不要編寫迫使它們這麼做的API。

String[] str = {"aaa", "bbb", "ccc", "ddd", "eee"};
		try{
			int i = 0;
			while(true)
				System.out.println(str[i++].toString());
		}catch(ArrayIndexOutOfBoundsException e){
			
		}
     以上程式碼就是使用不當的例子,利用基於異常的模式來迴圈陣列,這是不合理的,應該用標準模式。
String[] str = {"aaa", "bbb", "ccc", "ddd", "eee"};
		for(String s : str){
			System.out.println(s);
		}

    

     第58條:對可恢復的情況使用受檢異常,對程式設計錯誤使用執行時異常

     java程式設計語言提供了三種可丟擲結構:受檢的異常(checked exception),執行時異常(run-time exception)和錯誤(error)。

     如果期望呼叫者能夠適當地恢復,對於這種情況就應該使用受檢的異常。

     如果程式丟擲未受檢的異常或者錯誤,往往就屬於不可恢復的情形,繼續執行下去有害無益。

     用執行時異常來表明程式設計錯誤。大多數的執行時異常都表示前提違例,前提違例指API的客戶沒有遵守API規範建立的約定。例如,陣列訪問的約定指明瞭陣列的下標值必須是在0和陣列長度減1之間。

     錯誤往往被JVM保留用於表示資源不足、約束失敗,或者其他使程式無法繼續執行的條件。

     第59條:避免不必要地使用受檢的異常

     如果正確的使用API並不能阻止這種異常條件的產生,並且一旦產生異常,使用API的程式設計師可以立即採取有用的動作,這種負擔就被認為是正當的。除非以上兩條規則都成立,否則更適合於使用非受檢的異常。

     第60條:優先使用標準的異常

     使用標準的異常有益於程式碼重用。

     常用的異常

異常 使用場合
IllegalArgumentException 非null的引數值不正確
IllegalStateException 對於方法呼叫而言,物件狀態不合適
NullPointerException 在禁止使用null的情況下引數值為null
IndexOutOfBoundsException 下標引數值越界
ConcurrentModificationException 在禁止併發修改的情況下,檢測到物件的併發修改
UnsupportedOperationException 物件不支援使用者請求的方法

     第61條:丟擲與抽象相對應的異常

     更高層的實現應該捕獲低層的異常,同時丟擲可以按照高層抽象進行解釋的異常。這種做法被稱為異常轉譯。

     第62條:每個方法丟擲的異常都要有文件

     始終要單獨地宣告受檢的異常,並且利用javadoc的@throws標記,準確地記錄下丟擲每個異常的條件。

     第63條:在細節訊息中包含能捕獲失敗的資訊

     當程式由於未被捕獲的異常而失敗的時候,系統會自動地打印出該異常的堆疊軌跡。在堆疊軌跡中包含該異常的字串表示法,即它的toString方法的呼叫結果。異常型別的toString方法應該儘可能多地返回有關失敗原因的資訊,這一點特別重要。

     第64條:努力使失敗保持原子性

     失敗的方法呼叫應該使物件保持在被呼叫之前的狀態。有幾種途徑可以實現失敗原子性。

     第一種,設計一個不可變的物件,如果物件不可變,失敗原子性就是顯然的。

     第二種,對於在可變物件上執行操作的方法,獲得失敗原子性最常見的辦法是,在執行操作之前檢查引數的有效性。

     第三種,編寫一段恢復程式碼,由它來攔截操作過程中發生的失敗,以及使物件回滾到操作開始之前的狀態上。

     第四種,在物件的一份臨時拷貝上執行操作,當操作完成之後再用臨時拷貝中的結果代替物件的內容。

     第65條:不要忽略異常

     catch塊中不能是空的,至少包含一條說明,解釋為什麼可以忽略這個異常。