簡體   English   中英

為什么要在 Java 中使用嵌套的 try-catch 塊?

[英]Why should I use nested try-catch blocks in Java?

我真的不明白使用嵌套的 try-catch 塊的意義。 它們很難閱讀,有時也不是很簡單。 例如:

try {
 // do something
}
catch ( [exception_1] e) {}
catch ( [exception_2] e) {}
catch ( [exception_3] e) {}

上面的代碼更具可讀性,我可以理解它的作用——如果發生異常,它可以由 catch 塊之一處理。 但如果我使用嵌套形式:

try {
   try {
      try {
         // Do something for try-block 3
      }
      catch ( [exception_1] except_1) {};
      // Do something for try-block 2
   }
   catch ( [exception_2] except_2) {};
   // Do something for try-block 1
}
catch ( [exception_3] except_3) {}

上面的代碼是一團糟,但它實現的與第一個代碼完全相同。 還是沒有? 幫我解決這個問題。

嗯,這取決於你如何編寫代碼。 例如,如果將使用某些代碼...

try {
   try {
      -->in here<--
      try {
         // Do something for try-block 3
      }
      catch ( [exception_1] except_1) {};
      // Do something for try-block 2
   }
   catch ( [exception_2] except_2) {};
   // Do something for try-block 1
}
catch ( [exception_3] except_3) {}

那么如果引發了 exception_1,則不會被捕獲。 如果一切都將在第三次嘗試中使用,那么沒有區別。

好的 - 有點做作,但證明了兩個 try-catch 結構不同的觀點 - 取決於實際的實現(這可能正是@KosztDojscia 所指出的,所以然后考慮這個答案是重復的):

public class Main
{
    public static class Exception1 extends Exception { }
    public static class Exception2 extends Exception { }
    public static class Exception3 extends Exception { }
    
    public static void main(String[] args) {
        int i = 0;

        // "messy" structure
        try {
            try {
                try {
                    i = 3; if (i == 3) throw new Exception1();
                } catch (Exception1 e1) { i = 300; }

                i = 4; if (i == 4) throw new Exception2();
    
            } catch (Exception2 e2) { i = 400; }
            
            i = 5; if (i == 5) throw new Exception3();

        } catch (Exception3 e3) { i = 500; }
        
        System.out.println(i);

        // "clean" structure            
        try {
            i = 3; if (i == 3) throw new Exception1();
            i = 4; if (i == 4) throw new Exception2();
            i = 5; if (i == 5) throw new Exception3();
        } catch (Exception1 e1) { i = 300; }
          catch (Exception2 e2) { i = 400; }
          catch (Exception3 e3) { i = 500; }

        System.out.println(i);

    }
}

印刷:

500
300

嵌套的 try-catch 塊對於設置可能需要在中間階段進行一些中間處理的自動關閉資源非常有用,而不是在外部 try 塊中列出所有資源:

try(var autoClosedA = initResourceA()) {
    var somevar = someprocessingfor(autoClosedA);
    try(var autoClosedB = initResourceB(somevar)) {
        // Some processing
    }
} catch (SomeException | OtherException ex) {
    logger.error("Failed to handle XYZ on params: "+someparam, ex);
    throw ex;
}

請注意,您不一定需要在每個級別的異常處理中使代碼不整潔,因為以后的 JDK 允許重用相同的異常處理程序,如上所示。 您甚至不需要多個方法中的 catch,因為您可以將所有應用程序錯誤報告保留在應用程序的最高級別。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM