Java面試筆記之異常處理

針對Java面試題中的異常處理部分,特別地寫一篇博文來總結一下。不說廢話,先提出問題,再給出解決方案,再總結。走起!

1. 面試問題

基礎知識:

Q1:什麼是異常?什麼是錯誤?異常和錯誤的區別是什麼?

Q2:Java中的異常類的繼承結構

Q3:異常中的運行異常和檢查異常

Q4:try-catch-finally塊的使用

Q5:自定義異常類的使用

Q6: throw和throws的區別

高級知識:

Q1: finally塊什麼時候執行?finally塊一定會執行嗎?通常在finally塊執行什麼?finally塊執行內存優化的技巧和原因

Q2: 子類方法不應該拋出比父類方法更大範圍的異常

Q3:try-catch塊的使用注意事項

2. 問題解答

基礎知識:

A1:

異常指的是在Java程序運行的過程中發生的一些非正常的情況或者錯誤,針對非正常的情況或者錯誤的發生,Java可以通過try-catch-finally塊來捕獲異常從而處理異常,使得異常發生時,程序可以通過處理異常從而恢復原來的正常狀態,而不至於停止運行。錯誤則是在JVM層面上的錯誤,Java程序中不能通過try-catch-finally塊來捕捉錯誤,也就不能使得錯誤發生時,通過必要的手段處理恢復正常,錯誤發生時程序只能停止。

A2:Java異常類的繼承結構大概如下

A3:

運行時異常通常編譯器不會強制對其捕獲或者處理,都是通過JVM來處理

檢查異常通常編譯器會強制對其捕獲或者處理,發生在編譯階段

對比的表格內容如下:

類別 發生階段 是否強制 包含異常    

運行異常

發生在程序運行時

NullPointerException(空指針異常)

ArrayStoreException(數據存儲異常)

ClassCastException(類型轉換異常)

 

 

 

IndexOutofBoundExcpetion(數組越界異常)

BufferOverflowException(緩衝區溢出異常)

ArithmeticException(算法異常)

 

 

 

 

 

 

檢查異常

發生編譯時

IOException(IO讀寫異常)

SQLEception(SQL異常)

 

           

A4:

try{
監控的代碼塊
}
catch()
{
異常處理的代碼塊
}
finally{
回收資源,內存優化的代碼塊
}

A5:

新建一個自定義異常類來繼承exception類

public class ZeroException extends Exception {

    private String str;

    public void PrintStr()
    {
        System.out.println("throws ZeroException by"+str);
    }

    @Override
    public String toString() {
        return super.toString();
    }

    public void setStr(String str) {
        this.str = str;
    }

    public String getStr() {
        return str;
    }
}

然後在程序中拋出這個類,並使用try-catch處理

public class MemoryLeak {

    public static  void main(String[] args)
    {
        try{
           int c= divied(2,0);
            System.out.println("c is "+c);
        } catch (ZeroException e) {
            e.setStr("異常!被除數不能爲0!分母不能爲0!");
            e.PrintStr();
        }
        catch(Exception e)
        {
            e.printStackTrace();
        }
    }

    public static int divied(int x,int y ) throws ZeroException{

        if (y==0) {
            throw new ZeroException();
        }
        else
        {
            System.out.println("print divided by "+x/y);
            return x/y;
        }

    }

}

A6:

  1. throw通常出現在函數體內,表示要拋出這個異常。如果在某個函數聲明時throws了異常,那麼有需要通過try-catch塊來捕獲和處理異常,否則也會報錯
  2. 如果某個函數內部用throw拋出了異常,那麼在方法聲明中一定要配套使用throws,否則會報錯
  3. .throws通常出現在函數聲明的位置,表示這個方法可能要拋出這個異常

高級知識

A1:針對finally的深入瞭解,我們可以看這一篇文章

https://blog.csdn.net/qq_39135287/article/details/78455525

A2:子類方法不應該拋出比父類方法更大的異常的原因時,由於Java的設計原則,我們默認將父類方法應該充分考慮到運行環境的險惡程度,所以需要最大的限度地來捕獲和處理異常。如果子類拋出了比父類更大的範圍的異常,那麼子類處理了異常,父類應該怎麼辦呢?如果子類的拋出的異常由父類來處理,那麼拋出更大的異常時,由於父類並沒有定義其相關的異常處理,就無法處理子類的異常

A3: 

1. 儘量使用try-catch-finally塊來處理異常,在finally塊中應該儘可能的回收內存資源

2. 儘量減少try監控的代碼塊

3. 應該先用專業的異常來處理,再用exception來處理

4. 在catch語句塊中,不要簡單的拋出異常,更要儘可能的處理異常

5. 出現異常後,應當保證項目不能就此終止,要把異常造成的影響降到最低

3. 總結經驗

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章