2014-10-06 103 views
1

我有问题了解以下内容。 我有一个名为TestClass20类,当我编译和运行我得到下面的输出:在catch块中抛出NullPointerException

Exception in thread "main" MyException 
     at TestClass20.m1(TestClass20.java:21) 
     at TestClass20.main(TestClass20.java:17) 

//TestClass20.java

class MyException extends IllegalArgumentException{} 
public class TestClass20{ 
    public static void main(String[] args){ 
     TestClass20 tc = new TestClass20(); 
     try{ 
     tc.m1(); 
     } 
     catch (MyException e){ 


     tc.m2(); // THIS IS LINE 11 



     } 
     finally{ 
      tc.m1(); // THIS IS LINE 17 
     } 
    } 
    public void m1() throws MyException{ 
     throw new MyException(); //THIS IS LINE 21 
    } 
    public void m2() throws RuntimeException{ 
     throw new NullPointerException(); 
    } 
} 

我的问题是,为什么线11不抛出任何空指针异常。第11行调用了引发新的NullPointerException的m2()方法,所以我期望它抛出NullPointerException。我期待的输出应该是:

Exception in thread "main" java.lang.NullPointerException // Exception that should have been thrown by line 11 

然后

Exception in thread "main" MyException // Exception thrown by line 17. 

总结: 线11应该先抛出NullPointerException异常,然后第17行抛出MyException

如果我稍微改变代码对此:

//TestClass21.java

class MyException extends IllegalArgumentException{} 
public class TestClass21{ 
    public static void main(String[] args){ 
     TestClass21 tc = new TestClass21(); 


     tc.m2(); //LINE 7 




    } 
    public void m1() throws MyException{ 
     throw new MyException(); 
    } 
    public void m2() throws RuntimeException{ 
     throw new NullPointerException(); 
    } 
} 

然后我得到以下输出:

Exception in thread "main" java.lang.NullPointerException 
     at TestClass21.m2(TestClass21.java:17) 
     at TestClass21.main(TestClass21.java:7) 

那么,为什么在TestClass21.java NullPointerException异常打印,但它并没有TestClass20.java打印?是不可能在catch块中打印异常(NullPointerException或其他RuntimeException)?

任何解释将不胜感激。

感谢

+0

你有'tc.m1(); '在finally块中抛出MyException。 – 2014-10-06 14:55:46

+0

你为什么期望有什么不同? 'finally'块总是*被执行。即使在'try'范围内没有任何例外。 – 2014-10-06 15:34:43

回答

5

tc.m1();在finally块这样MyException被抛出。

最后总是得到执行,所以最后的异常是最后抛出的异常。并且是NullPointerException也被抛出,但在finally块中被MyException抑制。

从取出tc.m1(); finally块,你会看到你的NullPointerException

+0

谢谢苏比尔。这似乎回答了我的问题,虽然我不明白为什么NullPointerException被MyException禁止了 – 2014-10-06 15:22:29

+0

简单的答案是,这是因为只有一个异常可以退出try-catch-finally块。根据定义,它是“终于”抛出的。 – biziclop 2014-10-06 15:24:01

+0

优秀。谢谢 – 2014-10-06 15:24:42

1

我认为这是如何可以达到你想要的。

class MyException extends IllegalArgumentException{} 
public class TestClass20{ 
    public static void main(String[] args){ 
     TestClass20 tc = new TestClass20(); 
     try{ 
     tc.m2(); 
     } 
     catch (NullPointerException e){ 

     e.printStackTrace(); 

     } 
     finally{ 
      tc.m1(); 
     } 
    } 
    public void m1() throws MyException{ 
     throw new MyException(); 
    } 
    public void m2() throws NullPointerException{ 
     throw new NullPointerException(); 
    } 
} 
1

Java 7中引入了一个方法来处理这样的情况下,你可以使用ThrowableaddSuppressed()方法,发出信号,你的清理(你会放在一个finally块)没有正常完成。

try { 
     Exception e1 = null; 
     try { 
      throw new Exception("original"); 
     } catch(Exception ex) { 
      e1 = ex; 
      throw ex; 
     } 
     finally { 
      try { 
       throw new Exception("from finally"); 
      } catch(Exception e2) { 
       if (e1 != null) 
        e1.addSuppressed(e2); 
      } 
     } 
    } catch(Exception ex) { 
     System.out.println(ex.getMessage()); 
     for (Throwable t : ex.getSuppressed()) { 
      System.out.println("Suppressed: "+t.getMessage()); 
     } 
    } 

在Java 7中引入的try-with-resources构造也以类似的方式工作。

相关问题