十年網(wǎng)站開(kāi)發(fā)經(jīng)驗(yàn) + 多家企業(yè)客戶 + 靠譜的建站團(tuán)隊(duì)
量身定制 + 運(yùn)營(yíng)維護(hù)+專業(yè)推廣+無(wú)憂售后,網(wǎng)站問(wèn)題一站解決
好程序員Java教程分享Java系列之異常定義
創(chuàng)新新互聯(lián),憑借十載的成都網(wǎng)站設(shè)計(jì)、做網(wǎng)站、成都外貿(mào)網(wǎng)站建設(shè)公司經(jīng)驗(yàn),本著真心·誠(chéng)心服務(wù)的企業(yè)理念服務(wù)于成都中小企業(yè)設(shè)計(jì)網(wǎng)站有成百上千案例。做網(wǎng)站建設(shè),選創(chuàng)新互聯(lián)。
異常:就是程序在運(yùn)行的過(guò)程中遇到的種種不正常的情況。
特點(diǎn):如果一個(gè)程序在運(yùn)行中遇到了一個(gè)未經(jīng)處理的異常,則這個(gè)異常會(huì)終止程序的運(yùn)行。
? 但是如果程序出現(xiàn)的異常被處理了,此時(shí)程序不會(huì)被終止。所以我們需要知道怎么去處理異常。
其實(shí)在Java中,異常也是一個(gè)類。
類的體系:
- Throwable: 是所有的異常的根類
- Error: 發(fā)生在編譯器級(jí)別的,我們程序無(wú)法處理的錯(cuò)誤。
- Exception: 我們可以去處理的異常。
- RuntimeException:
異常的分類:可以分成兩種異常:
- 運(yùn)行時(shí)異常(Runtime Exception)
- 發(fā)生在程序運(yùn)行的過(guò)程中的異常。
- 如果不處理這種異常,程序可以正常編譯,但是當(dāng)執(zhí)行到異常產(chǎn)生的時(shí)候,會(huì)終止程序的運(yùn)行。
- 例如:NullPointerException、IndexOutOfBoundsException、ArithmeticException...
- 非運(yùn)行時(shí)異常(Non-Runtime Exception)
- 發(fā)生在程序編譯的過(guò)程中的異常。(編譯時(shí)異常)
- 如果不處理這種異常,程序?qū)o(wú)法進(jìn)行編譯。
- 例如:ParseException...
需要使用語(yǔ)法:try-catch-finally
語(yǔ)法:
try {
? // 這里寫(xiě)可能會(huì)產(chǎn)生異常的代碼。
? // 注意:
? // 一旦這里面的代碼產(chǎn)生了異常,從異常產(chǎn)生開(kāi)始往后所有try中的代碼都不再執(zhí)行,直接執(zhí)行指定的catch
}
catch(需要捕獲的異常類型 標(biāo)識(shí)符) {
? // 捕獲異常,如果try中產(chǎn)生的異常類型和我們要捕獲的異常類型匹配,此時(shí)會(huì)執(zhí)行這個(gè)代碼段中的內(nèi)容
? // 如果執(zhí)行到這里了,相當(dāng)于這個(gè)異常被捕獲、處理了,這個(gè)異常將不再終止程序的運(yùn)行。
}
finally {
? // 這里的代碼始終會(huì)執(zhí)行。
? // 無(wú)論try中的代碼有沒(méi)有異常產(chǎn)生,這里的代碼都會(huì)執(zhí)行。
? // 在這里我們一般情況下是做一些資源釋放的工作。
}
備注:
以上,是完整的try-catch-finally語(yǔ)句。但是實(shí)際在用的時(shí)候,try后面可以只有catch, 也可只有finally,但是不能什么都沒(méi)有。
- 一般情況下,catch我們是不會(huì)省略不寫(xiě)的。
- 如果try中的代碼可能產(chǎn)生的異常不止一種
- 如果需要對(duì)產(chǎn)生的不同異常進(jìn)行不同的處理,可以使用多個(gè)catch語(yǔ)句
- 多個(gè)catch語(yǔ)句的先后順序
- 如果多個(gè)catch中的異常,沒(méi)有繼承關(guān)系,則先后順序沒(méi)有影響
- 如果多個(gè)catch中的異常,有繼承關(guān)系,則子類異常在前,父類異常在后
- 如果需要對(duì)某些異常做同樣的處理,可以在同一個(gè)catch中,用 | 拼接所有要處理的異常。
- 這些用|拼接起來(lái)的異常之間,不能有繼承關(guān)系
- 如果需要對(duì)所有的異常做同樣的處理,可以在一個(gè)catch中捕獲一個(gè)父類異常。
public static int show(int a, int b) { int c = 0; try { c = a / b; // 能走到這里,說(shuō)明上面的除沒(méi)有異常。 return c; } catch (ArithmeticException e) { System.out.println("出現(xiàn)了一個(gè)算術(shù)異常"); return c; } finally { // 在return之前,執(zhí)行finally中的代碼段 System.out.println("finally中的代碼執(zhí)行了"); c = -10; } }
以上代碼段,在try和catch中都有return語(yǔ)句。
finally中的代碼始終會(huì)執(zhí)行,但是針對(duì)這種情況,他的執(zhí)行時(shí)機(jī):
先執(zhí)行return語(yǔ)句,此時(shí),將需要返回的值緩存起來(lái)。然后再去執(zhí)行finally語(yǔ)句中的代碼,執(zhí)行結(jié)束后,返回剛才緩存的那個(gè)值。
常用在某一個(gè)方法中,表示拋出一個(gè)異常對(duì)象。等在調(diào)用這個(gè)方法的時(shí)候去處理這個(gè)異常。
一個(gè)異常對(duì)象被實(shí)例化完成后,不具備任何意義。只有被throw關(guān)鍵字拋出了,才具備異常的功能。
- 常用在方法的聲明部分,用來(lái)描述這個(gè)方法可能會(huì)拋出什么異常,給調(diào)用這個(gè)方法的部分看的。
- 如果在方法中使用throw拋出了一個(gè)Runtime Exception:
- throws可以寫(xiě),也可以不寫(xiě)
- 備注:一般情況下,我們還是會(huì)按照實(shí)際情況進(jìn)行描述的。
- 如果在方法中使用throw拋出了一個(gè)Non-Runtime Exception:
- 此時(shí)throws必須寫(xiě)
- 可以在方法中不去處理異常,將異常處理提到調(diào)用這個(gè)方法的時(shí)候。
注意:在方法重寫(xiě)中
- 如果重寫(xiě)的方法拋出的是一個(gè)Non-Runtime Exception
- 子類方法拋出的異常需要父類方法拋出異常的子類型,或者等同于父類方法拋出的異常類型
- 不能讓子類重寫(xiě)的方法拋出異常的類型高于父類方法拋出的異常類型
系統(tǒng)給我們提供了很多的異常類,但是這些異常類并不能夠滿足我們所有的需求。這種情況下,我們就需要去自定義異常。繼承自異常類,寫(xiě)一個(gè)子類即可。
自定義RuntimeException
繼承自RuntimeException類,寫(xiě)一個(gè)子類。這個(gè)子類異常就是一個(gè)運(yùn)行時(shí)異常。
class NumberOfLegException extends RuntimeException { /** * 通過(guò)一個(gè)異常描述信息來(lái)實(shí)例化一個(gè)異常對(duì)象 * @param message */ public NumberOfLegException(String message) { // 怎么樣去設(shè)置這個(gè)異常信息? super(message); } }
自定義Non-Runtime Exception
繼承自Exception類,寫(xiě)一個(gè)子類。這個(gè)子類異常就是一個(gè)非運(yùn)行時(shí)異常。
class NumberOfLegException extends Exception { /** * 通過(guò)一個(gè)異常描述信息來(lái)實(shí)例化一個(gè)異常對(duì)象 * @param message */ public NumberOfLegException(String message) { // 怎么樣去設(shè)置這個(gè)異常信息? super(message); } }
在自定義異常類的時(shí)候,類名最好使用Exception作為結(jié)尾