異常是程序中的一些錯誤,但並不是所有的錯誤都是異常,並且錯誤有時候是可以避免的。比如說,你的代碼少
了一個分號,那麼運行出來結果是提示是錯誤java.lang.Error;如果你用System.out.println(11/0),那麼你是因為你用
0做了除數,會拋出java.lang.ArithmeticException的異常。Java異常是Java提供的用於處理程序中錯誤的一種機制。
異常發生的原因有很多,通常包含以下幾大類:a用戶輸入了非法數據。
b要打開的文件不存在。c網絡通信時連接中斷,或者JVM內存溢出。
這些異常有的是因為用戶錯誤引起,有的是程序錯誤引起的,還有其它一些是因為物理錯誤引起的。
要理解Java異常處理是如何工作的,你需要掌握以下三種類型的異常:
1)檢查性異常:最具代表的檢查性異常是用戶錯誤或問題引起的異常,這是程序員無法預見的。例如要打開一個
不存在文件時,一個異常就發生了,這些異常在編譯時不能被簡單地忽略。
2)運行時異常: 運行時異常是可能被程序員避免的異常。與檢查性異常相反,運行時異常可以在編譯時被忽略。
3)錯誤: 錯誤不是異常,而是脫離程序員控制的問題。錯誤在代碼中通常被忽略。例如,當棧溢出時,一個錯誤
就發生了,它們在編譯也檢查不到的。
當Java程序的執行過程中出現異常事件,可以生成一個異常類對象,該異常對象封裝了異常事件的信息並將它提
交給Java運行時系統,這個過程稱為拋出異常。
當Java運行時系統收到異常對象時,會尋找能處理這一異常的代碼並把它當前異常對象交給其處理,這一過程稱
為捕獲異常。
所有的異常類是從java.lang.Exception類繼承的子類。Exception類是Throwable類的子類。除了Exception類外,
Throwable還有一個子類Error 。Java程序通常不捕獲錯誤。錯誤一般發生在嚴重故障時,它們在Java程序處理的范
疇之外。Error用來指示運行時環境發生的錯誤。例如,JVM內存溢出。一般地,程序不會從錯誤中恢復。
異常類有兩個主要的子類:IOException類和RuntimeException類。
在Java 內置類中(接下來會說明),有大部分常用檢查性和非檢查性異常。
Java 語言定義了一些異常類在java.lang標准包中。標准運行時異常類的子類是最常見的異常類。由於java.lang包
是默認加載到所有的Java程序的,所以大部分從運行時異常類繼承而來的異常都可以直接使用。
Java根據各個類庫也定義了一些其他的異常,下面的表中列出了Java的非檢查性異常。
下面的表中列出了Java定義在java.lang包中的檢查性異常類。
下面的列表是Throwable 類的主要方法:
使用try和catch關鍵字可以捕獲異常。try/catch代碼塊放在異常可能發生的地方。try/catch代碼塊中的代碼稱為保
護代碼,使用 try/catch的語法如下:
try{ //程序代碼 }catch(ExceptionName e){ //catch塊 }
Catch語句包含要捕獲異常類型的聲明。當保護代碼塊中發生一個異常時,try後面的catch塊就會被檢查。如果發
生的異常包含在catch塊中,異常會被傳遞到該catch塊,這和傳遞一個參數到方法是一樣。如果try塊中確實拋出異
常,先終止程序執行,然後程序的控制權將被移交給catch塊中的異常處理程序。
實例:下面的例子中聲明有兩個元素的一個數組,當代碼試圖訪問數組的第三個元素的時候就會拋出一個異常。
Test.java源文件代碼:
import java.io.*; public class Test{ public static void main(String[] args){ try{ int a[] = new int[2]; System.out.println("Access element three :" + a[3]); }catch(ArrayIndexOutOfBoundsException e){ System.out.println("Exception thrown :" + e); } System.out.println("Out of the block"); } }
以上代碼編譯運行輸出結果如下:
上面的拋出的異常是說數字3引起的數組越界異常。
一個try代碼塊後面跟隨多個catch代碼塊的情況就叫多重捕獲。多重 catch 語句中,異常類型的書寫順序必須是子
類在前,父類在後。
多重捕獲塊的語法如下所示:
try{ // 程序代碼 }catch(異常類型1 異常的變量名1){ // 程序代碼 }catch(異常類型2 異常的變量名2){ // 程序代碼 }catch(異常類型2 異常的變量名2){ // 程序代碼 }
上面的代碼段包含了3個catch塊。可以在ry語句後面添加任意數量的catch塊。如果保護代碼中發生異常,異常被
拋給第一個catch塊。如果拋出異常的數據類型與ExceptionType1匹配,它在這裡就會被捕獲;如果不匹配,它會被
傳遞給第二個catch塊。如此,直到異常被捕獲或者通過所有的catch塊。
實例:展示了怎麼使用多重try/catch。
try{ file = new FileInputStream(fileName); x = (byte) file.read(); }catch(IOException i){ i.printStackTrace(); return -1; }catch(FileNotFoundException f){ f.printStackTrace(); return -1; }