Java基础(七)--Exception异常处理
發(fā)現(xiàn)錯(cuò)誤的理想時(shí)機(jī)是程序運(yùn)行之前(編譯期),然后不太現(xiàn)實(shí),很多異常無法被發(fā)現(xiàn)(特別是業(yè)務(wù)上的數(shù)據(jù)),需要在運(yùn)行時(shí)解決。
錯(cuò)誤恢復(fù)機(jī)制保證代碼健壯性的方式,異常處理在程序中很常見,也是必須的,必須考慮有可能發(fā)生的異常,才能保證程序的正常運(yùn)行。而且
一旦程序出現(xiàn)異常,異常處理及日志能幫助我們定位和解決異常。
概念:
Exception,是一種意外,不正常的現(xiàn)象。使用異常可以降低處理代碼的復(fù)雜度,如果不適用異常,就必須通過判斷去檢查錯(cuò)誤,而且可能在很
多地方都要判斷,使用異常,只需要在一個(gè)地方處理錯(cuò)誤,可以節(jié)省代碼,能夠把正常程序運(yùn)行和異常分開。
異常分為Error和Exception,繼承Throwable
1、Error:無法處理的異常,是一種錯(cuò)誤,最常見的就是OutOfMemoryError,jvm直接停止運(yùn)行
2、Exception:一般性的異常,只要能夠捕捉處理,就能保證程序正常運(yùn)行,比如NullPointerException、IndexOutOfBoundsException
Exception又分為:
1、運(yùn)行時(shí)異常RuntimeException:
我們將RuntimeException或其他繼承自RuntimeException的子類稱為unchecked Exception。RuntimeException即使不編寫異常處理的程序
代碼,依然可以編譯成功。這種異常在程序運(yùn)行過程中可能出現(xiàn),例如NullPointException、ClassCastException等
2、非運(yùn)行時(shí)異常RuntimeException:
其他繼承自Exception異常的子類稱為checked Exception,編譯器強(qiáng)制要求進(jìn)行捕獲處理,比如常見的IOExeption、SQLException,否則編
譯無法通過
如何處理異常?
異常處理方式常用的有兩種,分別如下:
1、try、catch、finally
public static void main(String[] args) {try { //要檢查的程序語句int i = 3/0;System.out.println("test");}} catch (ArithmeticException e) {System.out.println("ArithmeticException");} catch (Exception e) { //異常發(fā)生時(shí)的處理語句System.out.println("Exception Message: " + e.getMessage());throw e;} finally { //肯定會(huì)執(zhí)行的部分,無論是否發(fā)生異常System.out.println("finally Handler");}
} 結(jié)果:
ArithmeticException
finally Handler 總結(jié):
1、finally、catch都是可以省略的
2、catch可以有多個(gè),如果沒有異常,不會(huì)執(zhí)行,發(fā)生異常的話,按照順序匹配,如果匹配,就不會(huì)與后面的catch塊匹配
3、finally無論如何都會(huì)執(zhí)行,即使之前有return語句。通常在finally進(jìn)行資源釋放的代碼,或者lock的解鎖,某些業(yè)務(wù)場(chǎng)景等
PS:不要在finally使用return,因?yàn)闀?huì)覆蓋之前的return語句,很容易造成混淆
相比throws更加靈活,更好的控制程序流程
2、throw、throws
public int add(int i) throws Exception {if (i == 0) {throw new IllegalArgumentException();}return 0;
} throws:是把異常交給jvm進(jìn)行處理,把異常往上層拋出,一旦發(fā)生最終的結(jié)果可能就會(huì)程序終止(如果上層方法不進(jìn)行try catch),可以拋出
多個(gè)異常,一般需要在上層進(jìn)行try catch塊進(jìn)行處理。
throw:用于主動(dòng)拋出異常,throw關(guān)鍵字可以寫在任何地方,通常和業(yè)務(wù)有關(guān),通常這個(gè)異常時(shí)自定義和業(yè)務(wù)相關(guān)的Exception類
總結(jié)和建議:
1、父類或接口,對(duì)于子類是實(shí)現(xiàn)類的限制:
1.1).無論是繼承還是實(shí)現(xiàn),父類或者接口沒有拋出異常,實(shí)現(xiàn)類或子類不能拋出異常
public class A {public void f1() {}
}
public class B extends A{@Overridepublic void f1() throws IOException{System.out.println("");}
} 1.2).父類或者接口拋出異常Exception1,實(shí)現(xiàn)類或子類可以是否拋出異常都可以,如果拋出Exception2,不能是Exception1的父類
public class A {public void f1() throws IOException{}
}
public class B extends A{@Overridepublic void f1() throws Exception{System.out.println("");}
} 1.3).父類的方法拋出異常只有非運(yùn)行時(shí)異常(運(yùn)行時(shí)異常),則子類在重寫該方法的時(shí)候聲明的異常也只能有非運(yùn)行時(shí)異常(運(yùn)行時(shí)異常),
不能含有運(yùn)行時(shí)異常(非運(yùn)行時(shí)異常)。
public class A {public void f1() throws IOException{}
}
public class B extends A{@Overridepublic void f1() throws IOException,ClassNotFoundException{System.out.println("");}
} PS:類和接口在這方面的限制是相同的
2、throws一定是具體的Exception,而不是直接拋出Exception,否則上層必須也是拋出Exception,無法定位具體的異常
3、多catch塊的異常,一定是小異常在前面,否則可能永遠(yuǎn)無法捕捉到
4、謹(jǐn)慎使用異常,因?yàn)闀?huì)影響程序性能,能用判斷解決還是要判斷的
5、不要使用空的catch塊
6、異常處理盡量拋到最上層進(jìn)行統(tǒng)一處理
內(nèi)容參考:Java異常處理和設(shè)計(jì)和《Java異常處理》
轉(zhuǎn)載于:https://www.cnblogs.com/huigelaile/p/11015151.html
總結(jié)
以上是生活随笔為你收集整理的Java基础(七)--Exception异常处理的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: spring 组件基于注解的注册方式
- 下一篇: 第2节 mapreduce深入学习:4,