Java面向對象筆記 • 【第5章 異常處理】

全部章節   >>>>


本章目錄

5.1 異常概述

5.1.1 程序中的異常

5.1.2 異常分類

5.1.3 實踐練習

5.2 try-catch處理異常

5.2.2 使用finally回收資源

5.2.3 實踐練習

5.3 throws與throw

5.3.1 使用throws聲明拋出異常

5.3.2 使用throw拋出異常

5.3.3 實踐練習

5.4 自定義異常

5.4.1 創建自定義異常

5.4.2 自定義異常應用

5.4.3 實踐練習

總結:


5.1 異常概述

生活中的異常

程序中的異常

5.1.1 程序中的異常

Java語言中,異常是指程序在運行期間發生的事件導致程序中斷運行的正常指令流

例如,在算術運算中除數爲0、數組越界、空指針異常等,這些事件的發生都會阻止程序的正常運行

 

示例:演示除法運算

public class MathCalc {
	public static  int division(int dividend,int divisor){
		return  dividend/divisor;
	}
	public static void main(String[] args) {
		System.out.println(MathCalc.division(100, 0));
	}
}

 

5.1.2 異常分類

1、Throwable

位於異常類層次結構的頂端,它是Java中所有錯誤和異常的父

2、Error

通常指與虛擬機相關的問題,如系統崩潰、虛擬機錯誤、動態鏈接失敗等

這種錯誤無法恢復或不可能捕獲,將導致應用程序中斷。通常程序無法處理這些錯誤

3、Exeception

該類型的異常在程序中發生後可以進行捕獲處理,處理後程序正常運行,從而保證程序的穩定性及健壯性

Java程序開發中的異常處理,主要是針對Exception類及其子類進行

示例:演示數組下標越界異常

public class RunException {
	 public static void showRuntimeException(){
		 int[] data=new int[2];
		 System.out.println(data[2]);
	 }
	 public static void main(String[] args) {
	          RunException.showRuntimeException();	
	 }
}

分析:

  • 上述程序的數組長度爲2,數組中元素的索引範圍爲01,當程序取索引值1時,超出了索引的取值範圍,從而產生了數組下標越界
  • 由於沒有進行異常處理,程序立即終止
  • 該異常屬於運行時異常,其特點是:程序編譯時可通過,但運行時卻發生異常

常見運行時異常RuntimeException

異常類名稱

說明

ArithmeticException

算術異常

ArrayIndexOutOfBoundsException

數組索引爲負或大於等於數組大小異常

ClassCastException

對象轉換異常

IllegalArgumentException

調用方法時傳入非法參賽異常

IndexOutOfBoundsException

數組索引越界異常

NegativeArraySizeException

數組長度爲負值異常

NullPointerException

空指針指向異常

NumberFormatException

數字格式異常

StringIndexOutOfBoundsException

字符串索引越界異常

UnsupportedOperationException

操作錯誤異常

5.1.3 實踐練習

 

5.2 try-catch處理異常

Java異常處理的作用和運行機制:

Java的異常處理機制可以保障程序具有良好的容錯性,使程序健壯性更高。

當程序運行出現意外情形時,系統會自動生成一個Exception類型的子類對象來通知程序,從而實現業務功能的代碼與錯誤處理代碼分離,使程序具有更好的可讀性。

Java的異常處理機制提供了兩種方式來處理異常,一種是使用“try-catch”語句處理異常,另一種是在方法聲明時使用throws關鍵字將異常拋出。

語法:

try{
	//可能出現異常的語句
}catch(異常類型1 異常對象1){
          //異常處理代碼
}

示例:演示try-catch捕獲異常

try{
	//創建Scanner對象,用於接收控制檯輸入的數據
	Scanner input=new Scanner(System.in);
	System.out.println("請輸一個整數除數:");
	int num=input.nextInt();
	System.out.println("您輸入的數字是:"+num);
}catch(InputMismatchException e){
	System.err.println("輸入不匹配異常:程序只能接收整數");
}

注意:

try塊可以對應多個catch塊,構成多重catch語句塊,多重catch語句塊用於對多個不同 異常類型進行捕獲,但最多隻能選中一個執行

先處理小異常,再處理大異常。即進行異常捕獲時不僅應該將Exception類對應的catch塊放在最後,而且所有父類異常的catch  都應該放在子類異常catch塊的後面,否則將出現編譯錯誤。

示例:演示多重catch語句塊

try{
	Scanner input=new Scanner(System.in);
	System.out.println("請輸入被除數:");
	int divisor=input.nextInt();
	System.out.println("請輸出除數:");
	int dividend=input.nextInt();
	System.out.println("您輸入的兩個數的是:"+divisor/dividend);
}catch(InputMismatchException e){
	System.err.println("輸入不匹配異常:程序只能接收整數");
}
catch (ArithmeticException e) {
	System.err.println("算數異常:0不能作爲被除數");
}catch(Exception e){
	System.err.println("未知異常");
}	

注意:catch塊範圍大的異常放在後面

 
 

5.2.2 使用finally回收資源

語法:

try{
	//可能出現異常的語句
}catch(異常類型1 異常對象1){
          //異常處理代碼
} finally{
  //資源回收代碼
}

 

說明:

finally塊保證回收在try塊中打開的物理資源,如數據庫連接、網絡連接或磁盤文件

無論try語句塊中的代碼是否出現異常,try語句塊對應的任意一個catch語句塊是否被執行,甚至在trycatch語句塊中執行了return語句,finally塊總會被執行

無論是try語句塊還是catch語句塊中使用return語句,都要先執行完finally語句塊後,再返回當前方法

try語句不能獨立存在,其後至少要有一個catch語句塊或finally語句塊。

finally語句塊不是必須存在的,可以根據需求決定是否添加。

示例:使用try-catch-finally模擬文件操作過程中的異常處理

try{
	//創建Scanner對象,用於接收控制檯輸入的數據
	Scanner input=new Scanner(System.in);
	System.out.println("請輸一個整數除數:");
	int num=input.nextInt();
	System.out.println("您輸入的數字是:"+num);
}catch(InputMismatchException e){
	System.err.println("輸入不匹配異常:程序只能接收整數");
}

5.2.3 實踐練習

 
 

5.3 throws與throw

Java 強烈要求應用程序進行完整的異常處理。

throws用來聲明一個方法可能拋出的所有異常信息。通常不用顯示地捕獲異常,系統將自動將異常拋給上級方法,throws出現在方法的頭部。

throw指程序運行中拋出的一個具體的異常Exception,拋出的Exception需要用戶來捕獲處理。

語法:

[訪問控制符]  返回類型  方法名稱([參數列表])  throws  異常類1,  異常類2…
{
}

當前方法不知道如何處理當前異常時,可以使用throws關鍵字聲明拋出異常,該異常可由上一級調用者處理

throws聲明只能在方法簽名中使用

throws可以聲明拋出多個異常類,多個異常類之間以逗號隔開。

5.3.1 使用throws聲明拋出異常

示例:在讀取文件方法聲明時使用Throws拋出可能異常

public class Read {
	//使用throws拋出程序可能發生的異常類,可由調用該方法處捕獲處理
	public static void readFile() throws ClassNotFoundException,FileNotFoundException{
		//將com.java.Read類加載到JVM的內存中
		Class.forName("com.java.Read");
		//創建FileInputStream實例,用於讀取文件中的數據
		FileInputStream  fis=new FileInputStream("c://file.txt");
	}
	public static void main(String[] args) {
		try {
			Read.readFile();
		} catch (FileNotFoundException e) {
			e.printStackTrace();//顯示堆棧異常信息
		} catch (ClassNotFoundException e) {
			e.printStackTrace();
		}
	}
}

如果在main()方法中未使用try-catch捕獲readFile()方法拋出的異常,而是在main()中繼續將異常拋出,此時該異常交給JVM虛擬機進行處理

提倡開發人員在main()中將異常繼續向上拋給JVM

5.3.2 使用throw拋出異常

語法:

throw  異常類對象

在實際的企業項目開發中,系統是否要拋出異常,可能需要根據應用的業務需求來決定,如果程序中的數據處理與指定的業務需求不符,這就是一種異常

業務需求不符而產生的異常,必須由開發人員來決定拋出,系統無法拋出這種異常

如果需要在程序中自行拋出異常,則應該使用throw語句

throw語句拋出的不是一個異常類,而是一個異常實例,且每次只能拋出一個異常實例。

示例:使用throw拋出異常保證員工年齡合乎企業用人規則

public class UserInfo {
	private String name;
	private int age;
	...
	public void setAge(int age) throws Exception {
		if(age<18 || age>60){
			//使用throw拋出異常
			throw new Exception("員工年齡應該在18歲至60歲之間");
		}
		this.age = age;
	}
	...
	public static void main(String[] args) {
		UserInfo userInfo=new UserInfo();
		userInfo.setName("俞敏紅"); //姓名賦值
		try {
			userInfo.setAge(10);  //年齡賦值  
		    userInfo.showEmpInfo(); //顯示員工信息
		} catch (Exception e) {
			e.printStackTrace(); 
		}
	}
}

 

throwsthrow的區別

throws

throw

聲明一個方法可能拋出的所有異常類型

拋出一個具體的異常類實例

不用顯式地捕獲異常,可由系統自動將所有捕獲的異常信息拋給上級方法(即方法的調用者)

需要程序員自行捕獲相關的異常

throws在方法頭聲明

throw在方法內部使用

 

5.3.3 實踐練習


5.4 自定義異常

問題1:將員工的工資輸入爲負數。

問題2:將訂單的下單日期輸入爲超過當期時間。

。。。

5.4.1 創建自定義異常

自定義異常類需要繼承Exception

示例:創建自定義異常類

public class AuctionException extends Exception{
	//無參構造方法
	public  AuctionException(){
	}
	public AuctionException(String message){
		//調用父類有參構造器
		super(message); 
	}
}

5.4.2 自定義異常應用

1、異常處理的複雜性

異常不能由當前方法處理。

異常由當前方法處理一部分,另一部分交由當前方法的調用者進行處理,此時需要在當前方法中拋出異常。

2、多個方法相互協作處理異常

 

示例:使用自定義異常處理拍賣過程中的錯誤操作(亦可說使用自定義異常處理拍賣過程中的業務邏輯異常)。

public class AuctionTest {
	private double initPrice=30; //起拍價
	public void bid(String bidPrice) throws AuctionException{
		double d=0;
		try {
			//將字符串格式的小數轉換爲double類型的數據
			d=Double.parseDouble(bidPrice);			
		} catch (Exception e) {
			e.printStackTrace();
			//拋出自定義異常
			throw new AuctionException("輸入的競拍價格必須爲小數格式");
		}
		if(initPrice>d){
			//如果競拍價格低於起拍價格,則視爲異常,使用throw拋出自定義異常對象
			throw new AuctionException("競拍價格低於起拍價格,不許競拍");
		}
		initPrice=d;
	}
	
public class AuctionTest {	
	public static void main(String[] args) {
		Scanner input=new Scanner(System.in);
		System.out.println("請輸入商品的競拍價格:");
		AuctionTest  auctionTest=new AuctionTest();
		try {
			auctionTest.bid(input.next());
		} catch (AuctionException e) {
		  //捕獲bid()方法拋出的異常,顯示異常提示信息
		   System.out.println(e.getMessage());
		}
	}
}	

5.4.3 實踐練習

 

總結:

  1. Java的異常處理機制可以保障程序具有良好的容錯性,使程序健壯性更高。ExceptionJava異常的父類
  2. 運行時異常的父類是RuntimeException,它的特點是程序編譯時可通過,但運行時卻發生異常。常見的運行時異常有:ArithmeticExceptionArrayIndexOutOfBoundsExceptionNullPointerExceptionClassCastExceptionIllegalArgumentException
  3. Java的異常處理機制提供了兩種方式來處理異常,一種是使用“try-catch”語句處理異常,它將可能發生異常的代碼放在try塊,異常處理代碼放在catch塊;另一種是在方法聲明時使用throws關鍵字將異常拋出,拋出的異常由調用者進行處理
  4. finally塊保證回收在try塊中打開的物理資源,如數據庫連接、網絡連接或磁盤文件等
  5. 在方法中可以使用throw主動拋出一個異常對象。
  6. 自定義異常類需要繼承自Exception,定義合適的自定義異常可以解決業務邏輯規則的不正常情況。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章