Java 'throws' clause not needed when throwing a new NPE? and why does adding “throws Exception” give compilation errors?
我对'throws'子句感到好奇,并编写了下面的一段代码(我使用Eclipse和Java7)。 最初我只使用第1和第5块开始(期待编译错误,但没有发生......)然后这导致我编写其他块。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 | // 1 public void throwNPE() { throw new NullPointerException(); } // 2 public void throwNPEWithGenericClause() throws Exception { throw new NullPointerException(); } // 3 public void throwNPEWithNPEClause() throws NullPointerException { throw new NullPointerException(); } // 4 public void throwNPEWithIAEClause() throws IllegalArgumentException { throw new NullPointerException(); } // 5 public void callThrowNPE() { throwNPE(); } // 6 public void callThrowNPEWithGenericClause() { throwNPEWithGenericClause(); // COMPILATION ERROR } // 7 public void callThrowNPEWithNPEClause() { throwNPEWithNPEClause(); } // 8 public void callThrowNPEWithIAEClause() { throwNPEWithIAEClause(); } |
说实话,我原以为:
(a)1.中的编译错误(未处理的异常?我的方法不应该通知任何'后续调用者'这会抛出某种异常吗?)
(b)4中的某种问题(可能是编译错误?我在IAE中抛出NPE)
(c)5. 6. 7.和8中的编译错误。(未处理的异常?我省略了'throws'子句)
(d)也许有人也可以告诉我为什么6.是唯一一个我得到编译错误的...
Java中的异常可以分为三种不同的基类型:
错误(如果发生致命错误,则由JVM抛出)
异常(所有已检查的异常都继承自此异常)
RuntimeException(所有未经检查的异常都从此继承)
所有都是Throwables
未选中RuntimeException,因此当您抛出RuntimeException的异常子类时,编译器不会发出警告。如果您需要编译器来警告您,那么您应该使用Exception或其子类。
1)
所以编译器不会给出任何错误。
2)即使您的方法抛出NullPointerException,因为您使用throws Exception标记了该方法,编译器会警告您在其调用者中捕获它。
3)与第一个答案相同
4)与第一个答案相同
5)throwNPE根本不会抛出任何东西。
6)尽管你在throwNPEWithGenericClause中抛出NullPointerException(RuntimeException),因为你将方法标记为checked exception,编译器不允许。
7,8)与第一个答案相同。两个运行时异常,无需检查。
RuntimeException或未经检查的异常实例(如NPE)不需要抛出/捕获。它们可以被捕获,但通常你不想这样,因为它表示程序流程异常,它应该终止程序。通常,如果没有可能继续,那么它将作为RuntimeException终止。如果要阻止对null值执行某种操作,则应检查它是否为null而不是期望NPE。