一、例外?
java系統中將java.lang.Throwable類作為例外的最根類
[java.lang.Throwable是所有例外或錯誤的頂級類,可以處理任何例外]
* java.lang.Throwable
* |-----java.lang.Error:一般不撰寫針對性的代碼進行處理,
* |-----java.lang.Exception:可以進行例外的處理
* |------編譯時例外(checked)
* |-----IOException
* |-----FileNotFoundException
* |-----ClassNotFoundException
* |------運行時例外(unchecked,RuntimeException)
* |-----NullPointerException
* |-----ArrayIndexOutOfBoundsException
* |-----ClassCastException
* |-----NumberFormatException
* |-----InputMismatchException
* |-----ArithmeticException
二、例外分類
Throwable是所有例外或錯誤的頂級類,可以處理任何例外.
因為處理范圍過大,操作不方便,Java提供兩個子類:Exception和Error
例外分為: Exception(可以治療) 和 Error(不治之癥)
1. Error:
通常指 java系統出現的錯誤,與java程式無關. 無法使用代碼進行維護或修改錯誤.
2. Exception:
通常指 java程式出現的錯誤,可以使用代碼進行修改或維護.[通常值學習/研究 Exception.]
Exception的分類: [根據 編譯時 是否檢查 含有XX例外分類]
須查例外[非運行時例外]: 指 java檔案編譯為class檔案時, 需要檢查的例外.
不須查例外[運行時例外]: 指 java檔案編譯為class檔案時, 不需要檢查的例外.
3. 哪些例外屬于須查例外,哪些例外屬于不須查例外?
Exception及其子類[不含RuntimeException]都屬于須查例外[非運行時例外]
RuntimeException及子類屬于不須查例外也就是運行時例外
4. 常見的須查例外(編譯時例外):
語法錯誤 路徑錯誤 等等
5. 常見的不須查例外(運行時例外):
陣列下標越界:java.lang.ArrayIndexOutOfBoundsException,Java程式試圖訪問不存在的索引對應的元素.
被除數為0: java.lang.ArithmeticException: / by zero,在計算機中,被除數不能為0.
空指標:java.lang.NullPointerException,Java程式試圖去訪問不存在的物件的屬性或方法,因此報錯.
三、例外處理
使用try-catch-finally處理編譯時例外,使得程式在編譯時就不報錯,但是運行是仍然可能報錯
開發中由于運行時例外常見,通常不針對運行時例外try-catch-finally處理,而針對編譯時例外,一定要考慮例外的處理
throws的方式知識將例外拋給了方法的呼叫者,并沒有真正的將例外處理
1. 第一種: [積極處理]
try{
存放可能發生例外的代碼,try代碼塊將自動捕捉例外
}catch(例外型別 引數){
與發生的例外進行匹配,匹配上后將執行此處代碼
}catch(例外型別 引數){
與發生的例外進行匹配,匹配上后將執行此處代碼
}finally{
作為程式最后執行的代碼,一定會執行,即使try和catch里面有return或例外
}
說明:
- try,catch,finally代碼塊不能單獨使用,必須混合. 常見組合方式:try,catch,finally 或 try catch 或 try finally
- try代碼塊必須含有,catch代碼可以含有N個.finally代碼塊可以含有0或1個,且必須放在try和catch的后面.
原理:
- java程式執行try代碼塊中的代碼,如果發生例外,將被try代碼塊捕獲,
- try代碼塊捕獲例外后, 將于之后的catch代碼塊進行例外型別匹配,如果匹配上例外型別,將執行執行此處的catch代碼塊,不再向下繼續匹配.
- try代碼塊捕獲例外后,與所有的catch代碼塊的例外型別都不匹配,該例外將交給java系統處理[直接結束程式的執行]無論程式是否發生例外,例外是否處理成功,都將執行finally代碼塊[通常用于執行關鍵性的代碼: 關閉資源等等,降低程式的損失
注意: 當有多個catch代碼塊時,將處理范圍大的例外放在后面.
try中的例外物件匹配到某一個catch時,就會進入到catch中進行例外的處理,一旦處理完成,就退出當前的try-catch結構(在沒有寫finally的時候),繼續執行其后的代碼
常用的處理方式:
都是列印錯誤資訊,方式不同
public void test1() {
String str = "abc";
try {
int num = Integer.parseInt(str);
}catch(Exception e) {
// 1. System.out.println(e.getMessage());
// 2. e.printStackTrace();
}
}
快捷操作

2. 第二種: [消極處理]
格式:
權限.... 方法名(引數型別 引數名,引數型別 引數名,...) throws 例外型別,...{
方法體
}
原理:
- 當前方法體中將例外拋出到方法呼叫處,在方法呼叫的地方必須處理當前例外.
- 方法呼叫處可以處理該例外,也可以繼續向方法外拋出例外.[如果main函式中也沒有處理該例外,該例外將拋給Java系統,Java系統將以"粗暴的方式"處理,直接結束程式的執行]
- 例外后面的代碼就不會再執行了
方法重寫的規則之一:
類重寫的方法拋出的例外型別不大于父類被重寫的方法拋出的例外型別
import java.io.FileNotFoundException;
import java.io.IOException;
public class OverrideTest {
public static void main(String[] args) {
OverrideTest test = new OverrideTest();
test.display(new SubClass());
}
public void display(SuperClass s){
try {
s.method();
} catch (IOException e) {
e.printStackTrace();
}
}
}
class SuperClass{
public void method() throws IOException{
}
}
class SubClass extends SuperClass{
public void method()throws FileNotFoundException{
}
}
3. 開發中如何選擇使用try-catch-finally 還是使用throws?
-
如果父類中被重寫的方法沒有throws方式處理例外,則子類重寫的方法也不能使用throws,意味著如果子類重寫的方法中有例外,必須使用try-catch-finally方式處理,
-
執行的方法a中,先后又呼叫了另外的幾個方法,這幾個方法是遞進關系執行的,我們建議這幾個方法使用throws的方式進行處理,而執行的方法a可以考慮使用try-catch-finally方式進行處理,
四、手動拋出例外
throw
public class StudentTest {
public static void main(String[] args) {
try {
Student s = new Student();
s.regist(-1001);
System.out.println(s);
} catch (Exception e) {
// e.printStackTrace();
System.out.println(e.getMessage());
}
}
}
class Student{
private int id;
public void regist(int id) throws Exception {
if(id > 0){
this.id = id;
}else{
// System.out.println("您輸入的資料非法!");
//手動拋出例外物件,運行時例外,可以不用try-catch
// throw new RuntimeException("您輸入的資料非法!");
// 必須進行try-catch
throw new Exception("您輸入的資料非法!");
//錯誤的
// throw new String("不能輸入負數");
}
}
@Override
public String toString() {
return "Student [id=" + id + "]";
}
}
五、 自定義例外
如何自定義例外類?
- 繼承于現有的例外結構:RuntimeException 、Exception
- 提供全域常量:serialVersionUID
- 提供多載的構造器
public class MyException extends Exception{
static final long serialVersionUID = -7034897193246939L;
public MyException(){
}
public MyException(String msg){
super(msg);
}
}
此時使用自己定義的例外類
package com.atguigu.java2;
public class StudentTest {
public static void main(String[] args) {
try {
Student s = new Student();
s.regist(-1001);
System.out.println(s);
} catch (Exception e) {
// e.printStackTrace();
System.out.println(e.getMessage());
}
}
}
class Student{
private int id;
public void regist(int id) throws Exception {
if(id > 0){
this.id = id;
}else{
throw new MyException("不能輸入負數");
}
}
@Override
public String toString() {
return "Student [id=" + id + "]";
}
}
六、問題

進入A----用A方法----制造例外----進入方法B-----呼叫B
1. 請解釋Error和Exception的區別?
- Error:指的是JVM錯誤,這個時候的程式并沒有執行,無法處理;
- Exception:指的是程式之中出現的錯誤資訊,可以進行例外處理,主要關心Exception,
2. 請解釋java之中的例外處理流程
- 如果程式之中產生了例外,那么會自動的由JVM根據例外的型別,實體化一個指定例外類的物件;
- 如果這個時候程式之中沒有任何的例外處理操作,則這個例外類的實體化物件將交給JVM進行處理,而JVM的默認處理方式就是進行例外資訊的輸出,而后中斷程式執行
- 如果程式之中存在了例外處理,則會由try陳述句捕獲產生的例外類物件
- 與try之后的每一個catch進行匹配,如果匹配成功,則使用指定的catch進行處理,如果沒有匹配成功,則向后面的catch繼續匹配,如果沒有任何的catch匹配成功,則這個時候將交給JVM執行默認處理
- 不管是否有例外都會執行finally程式,如果此時沒有例外,執行完finally,則會繼續執行程式之中的其他代碼,如果此時有例外沒有能夠處理(沒有一個catch可以滿足),那么也會執行finally,但是執行完finally之后,將默認交給JVM進行例外的資訊輸出,并且程式中斷
3. 請解釋一下RuntimeException和Exception的區別?請列舉出幾個常見的RuntimeException
七、總結

throw 和 throws區別:
throw 表示拋出一個例外類的物件,生成例外物件的程序,宣告在方法體內,
throws 屬于例外處理的一種方式,宣告在方法的宣告處,
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/145708.html
標籤:Java
上一篇:MyBatis框架高級應用詳解
