## Java編程那些事兒82——異常處理語法1
陳躍峰
出自:[http://blog.csdn.net/mailbomb](http://blog.csdn.net/mailbomb)
### 10.3 異常處理語法
為了方便程序員進行異常的處理,在Java語言中創建了一套語法,這些語法主要分為以下幾個部分:
1、拋出異常
當程序運行時,如果發現異常的情況,通過生成對應的異常對象,并將該異常對象傳遞給Java的運行時系統,使得系統中包含該異常信息,這樣的過程被稱作拋出異常。
拋出異常是整個異常處理機制的起點,也是異常的發源地,一般出現在項目底層的代碼中。
2、聲明異常
當一個方法在執行時,除了能夠完成正常的功能以外,還可以出現一些異常情況,為了提醒調用該方法的程序員注意處理這些異常情況,需要在方法的聲明中將這些異常聲明出來,這就是聲明異常。
聲明異常的語法使得異常處理更加容易進行實現。
3、捕獲異常及異常處理
當異常被拋出以后,如果不進行處理,則異常會在方法調用過程中一直進行傳遞,直到最后一個方法,在J2SE中也就是main方法,最終將顯示在控制臺。
在實際項目中,當異常被拋出以后,需要首先捕獲到該異常,按照異常的種類不同,分別進行處理。
4、聲明自定義異常類
雖然在JDK API中提供了幾百個異常類,但是這些異常所代表的還只是常見的異常情況,在實際使用時還是無法代表所有的異常情況,所以Java語言運行聲明自定義的異常類,使用這些自定義的異常類來代表實際項目中JDK API無法代表的異常情況。
下面依次詳細介紹一下這些語法的相關規則。
### 10.3.1 拋出異常
在書寫項目中相關的底層基礎代碼時,相關的方法除了實現應該實現的功能以外,還需要考慮到各種異常情況,如果出現該代碼所在的方法無法處理的異常情況時,則應該在該方法內部拋出對應類型的異常時,使得整個方法的邏輯比較嚴謹。
例如,下面是一個實現將十進制數字轉換為二進制或8進制字符串的方法:
~~~
?????????/**
???????? ?* 將自然數轉換為二進制或八進制字符串
???????? ?* @param value 需要轉換的自然數
???????? ?* @param radix 基數,只能取2或8
???????? ?* @return 轉換后的字符串
???????? ?*/
???????? public static String toString(int value,int radix){
?????????????????? if(value == 0){
??????????????????????????? return "0";
?????????????????? }
?????????????????? StringBuffer s = new StringBuffer();
?????????????????? int temp; //余數
?????????????????? while(value != 0){ //未轉換結束
??????????????????????????? temp = value % radix;? //取余數
??????????????????????????? s.insert(0,temp);? //添加到字符串緩沖區
??????????????????????????? value /= radix;? //去掉余數
?????????????????? }
?????????????????? return s.toString();
???????? }
~~~
在該方法中使用除n取余的方法,將參數value轉換為對應的字符串,當在main方法中以書寫如下代碼時:
System.out.println(toString(12,2));
則程序的運行結果是:
1100
這樣在正常的情況下,程序獲得了正確的結果,但是該方法由于邏輯的限制,只能實現將“自然數”轉換為“二進制或八進制”字符串,如果在其它程序員誤傳入非法的參數時,則程序會獲得不正常的結果,例如書寫如下調用的代碼時:
System.out.println(toString(12,16));
則程序的運行結果是:
12
這個結果在轉換的邏輯上就是錯誤的。這樣就因為其它程序員誤傳入非法參數而出現了錯誤的結果。如果該方法作為實際項目的一個邏輯存在,則會由于該方法的問題導致后續其它的功能也發生錯誤,這是每個程序員都不希望看到的。
所以該方法雖然在功能上達到了要求,但是邏輯還是不嚴謹的,還需要在其它程序員調用該方法時傳入非法參數這樣的異常情況時,將這種異常報告出來,這就需要拋出異常的的代碼了。
拋出異常的語法格式為:
throw 異常對象;
例如:
throw new NullPointerException();
或
IllegalArgumentException e = new IllegalArgumentException();
throw e;
該代碼書寫在方法或構造方法的內部。該語法中,使用throw關鍵字,后續為代表對應異常情況的異常類類型的對象。當系統執行到該代碼時,將中止當前方法的執行,而直接返回到調用該方法的位置。所以在該代碼下面不能直接書寫其它的代碼,因為這些代碼將永遠無法執行到。例如:
throw new NullPointerException();
int n = 10;? //語法錯誤,該代碼無法到達
按照該語法,則上面的轉換方法改造以后的代碼如下:
~~~
???????? /**
???????? ?* 將自然數轉換為二進制或八進制字符串
???????? ?* @param value 需要轉換的自然數
???????? ?* @param radix 基數,只能取2或8
???????? ?* @return 轉換后的字符串
???????? ?*/
???????? public static String toString(int value,int radix){
?????????????????? //判斷異常的代碼
?????????????????? if(value <0){
??????????????????????????? throw new IllegalArgumentException("需要轉換的數字不是自然數!");
?????????????????? }
?????????????????? if(radix != 2 && radix != 8){
??????????????????????????? throw new IllegalArgumentException("進制參數非法");
?????????????????? }
?????????????????? if(value == 0){
??????????????????????????? return "0";
?????????????????? }
?????????????????? StringBuffer s = new StringBuffer();
?????????????????? int temp; //余數
?????????????????? while(value != 0){ //未轉換結束
??????????????????????????? temp = value % radix;? //取余數
??????????????????????????? s.insert(0,temp);? //添加到字符串緩沖區
??????????????????????????? value /= radix;? //去掉余數
?????????????????? }
?????????????????? return s.toString();
???????? }
~~~
這里,當value的值小于0時,則拋出非法參數異常,當radix的值不是2或8時,則拋出非法參數異常。
這樣在執行如下代碼:
~~~
???????? System.out.println(toString(12,2));
???????? System.out.println(toString(12,16));
~~~
則程序的執行結果是:
1100
Exception in thread "main" java.lang.IllegalArgumentException: 進制參數非法
at ThrowException.toString(ThrowException.java:22)
at ThrowException.main(ThrowException.java:7)
這里當參數符合要求時,則輸出正確結果1100,如果參數不合法,則拋出異常,由于異常沒有得到處理,則將終止程序的執行,則控制臺輸出異常的信息,并顯示異常的類型以及異常出現的位置。
這樣,就通過拋出異常的語法,使得該方法的邏輯比較嚴謹,在方法的參數不合法,即出現異常情況時,將這個異常報告出來,使得該方法不會出現錯誤的結果。
另外,拋出的異常將傳遞給運行時系統,這樣就將這種異常的情況傳遞出來,提醒其它的結構進行處理。
### 10.3.2 聲明異常
異常雖然被拋出了,但是由于拋出異常的代碼是在方法或構造方法的內部的,在調用方法或構造方法時一般是無法看到方法或構造方法的源代碼的,這樣調用的程序員就無法知道該方法或構造方法將出現怎樣的異常情況,所以需要有一種語法,可以使得調用的程序員可以看到被調用的結構可能出現的異常情況,這就是聲明異常的語法。
聲明異常的語法類似于藥品上的副作用說明,在患者服用藥品時,知道藥品的正常功能,但是無法詳細了解藥品的成分以及每種成分的含量(類似于源代碼),但是在藥品的說明上都有副作用的說明,例如過敏者不能服用等,這些和聲明異常的語法在功能上是類似。
聲明異常的語法格式為:
throws 異常類名
例如:
public static void test(int n) throws IllegalArgumentException,IOException
public Test()throws IllegalArgumentException
該語法使用在方法和構造方法的聲明以后,在throws關鍵字以后,書寫該方法或構造方法可能出現的異常,在這里需要書寫異常類的類名,如果有多個,則使用逗號分隔這些異常類名即可。
這里需要注意的是:
1、這些異常必須是該方法內部可能拋出的異常
2、異常類名之間沒有順序
3、屬于RuntimeException子類的異常可以不書寫在throws語句以后,但是另外一類異常如果可能拋出則必須聲明在throws語句之后
通過在對應的方法或構造方法聲明中書寫throws語句,使得調用該方法或構造方法的程序員可以在調用時看到對應結構可能出現的異常情況,從而提示對于這些異常情況進行處理,從而增強程序的健壯性。
而且即使在程序由于未處理對應的異常而導致程序在運行時出現錯誤時,也可以使程序員可以通過對應的提示獲得錯誤的原因,并指導程序員進行邏輯的修正,這樣都可以提高程序編寫時的效率,也可以使程序員更加容易的編寫出邏輯嚴謹的代碼,從而增加項目的質量,提高程序的穩定性。
但是聲明異常以后,異常還是存在的,異常還沒有獲得處理,在異常體系中最重要的還是捕獲到異常,然后針對異常的類型不同作出對應的處理。
- 前言
- (1)序言
- (2)程序設計是什么?
- (3)你適合學習程序設計嗎?
- (4)如何學好程序設計?
- (5)程序設計介紹小結
- (6)計算機軟件基本概念
- (7)進制的概念
- (8)計算機內部的數據表達
- (9)網絡編程基礎
- (10)Java語言簡介
- (11)JDK的獲得、安裝和配置
- (12)第一個HelloWorld程序
- (13)Eclipse基本使用
- (14)Eclipse基礎使用進階
- (15)如何學好Java語法
- (16)代碼框架、關鍵字和標識符
- (17)基本數據類型
- (18)變量和常量
- (19)數據類型轉換
- (20)空白、語句結束和注釋
- (21)算術運算符
- (22)比較運算符
- (23)邏輯運算符
- (24)賦值運算符
- (25)位運算符
- (26)移位運算符
- (27)其它運算符
- (28)運算符優先級
- (29)表達式
- (30)流程控制基礎
- (31)if語句語法(1)
- (32)if語句語法(2)
- (33)if語句語法(3)
- (34)switch語句語法
- (35)while語句語法
- (36)do-while語句語法
- (37)for語句語法
- (38)break和continue語句
- (39)流程控制綜合示例1
- (40)流程控制綜合示例2
- (41)流程控制綜合示例3
- (42)流程控制綜合練習
- (43)數組概述
- (44)數組基礎語法
- (45)數組使用示例1
- (46)數組使用示例2
- (47)數組使用示例3
- (48)多維數組基礎
- (49)多維數組使用示例1
- (50)多維數組使用示例2
- (51)多維數組練習
- (52)方法聲明
- (53)方法聲明示例
- (54)方法調用
- (55)方法重載和參數傳遞
- (56)方法練習
- (57)面向對象基礎
- (58)類(一)
- (59)類(二)
- (60)對象
- (61)面向對象設計方法和面向對象特性(一)
- (62)繼承(二)
- (63)多態性
- (64)訪問控制符、修飾符和其它關鍵字
- (65)static修飾符
- (66)final修飾符
- (67)this和super
- (68)抽象類和接口(一)
- (69)抽象類和接口(二)
- (70)抽象類和接口(三)
- (71)內部類簡介
- (72)包的概念
- (73)JDK文檔使用
- (74)java.lang包介紹1
- (75)String類使用
- (76)StringBuffer類和System類
- (77)包裝類
- (78)時間和日期處理
- (79)Random隨機處理
- (80)集合框架簡述
- (81)異常處理概述
- (82)異常處理語法1
- (83)異常處理語法2
- (84)IO簡介
- (85)IO類體系
- (86)文件操作之File類使用
- (87)文件操作之讀取文件
- (88)文件操作之寫文件
- (89)讀取控制臺輸入
- (90)裝飾流使用1
- (91)裝飾流使用2
- (92)IO使用注意問題
- (93)多線程基礎
- (94)多線程實現方式1
- (95)多線程實現方式2
- (96)多線程使用示例1
- (97)多線程使用示例2
- (98)多線程問題及處理1
- (99)多線程問題及處理2
- (100)多線程問題及處理3
- (101)網絡編程概述
- (102)網絡編程技術1
- (103)網絡編程技術2
- (104)網絡編程技術3
- (105)網絡編程技術4
- (106)網絡編程技術5
- (107)網絡協議概念
- (108)網絡編程示例1
- (109)網絡編程示例2
- (110)網絡編程小結