有时我想编写一个error()函数,它最终肯定会调用System.exit(),这意味着该函数永远不会返回。但是,如果我在其他函数中调用error(),我想写如:
int fun() {
...
error();
}
但是编译器坚持在error()调用之后返回一个int值,因为它不知道error()永远不会返回。 我肯定会返回一个任意的int,但如果返回类型是一个复杂的类,我需要在代码中构造它,这是浪费时间。有没有办法告诉编译器函数永远不会返回?
答案 0 :(得分:5)
你应该抛出RuntimeException。
答案 1 :(得分:5)
在Java方法签名中,您无法告诉编译器该方法无法返回。没有它,编译器别无选择,只能假设它可能会返回。 (实际上,JLS关于可达性/明确赋值的规则将明确说明......如果你愿意通过它们。)
我在两种方法之间摇摆不定:
int fun() {
...
error();
return 0; // NOT REACHED
}
和
int fun() {
...
error();
throw new AssertionError("not reached");
}
两者都不完全令人满意。
在第一个版本中,评论很重要,因为有人第一次阅读您的代码可能没有意识到error
永远不会返回。
第二个版本更强大,因为如果有人更改了error
方法的行为以便它实际返回,它会给你“快速失败”。 (第一个版本将导致fun
方法返回虚假值......可能导致其他意外后果。)
在相关点上,通过调用System.exit()
来拉动JVM上的插件的方法可能会有问题。更好的想法是抛出一个未经检查的“结束世界”异常并将其捕获到主线程的最外层。对于在其他线程上抛出的异常,一个想法是安装一个默认的未捕获异常处理程序,它使用Thread.interrupt()
通知主线程已抛出“结束世界”异常。
但重点是代码中的System.exit()
次调用是有问题的;例如如果您重新调整代码以在更大的框架内运行;例如在一个网络容器中。
答案 2 :(得分:3)
Java不允许您声明方法永远不会返回,但编译器知道永远不会返回的语句:throw
。
你可以通过声明你的“不回报”来解决这个问题。返回RuntimeException
的方法,并使用throw error()
进行调用。这样你就可以改变一个不返回"的方法的问题。到一个不返回"的语句。
由于您的error()
方法永远不会返回,因此您无需实际返回已声明的RuntimeException
,并且throw
中的throw error()
永远不会被执行。< / p>
这种技术还可以防止error()
返回时出现错误,可能是因为某些错误的条件代码。
示例:
private RuntimeException error() {
throw new EndOfTheWorldException();
// Java knows that code after throw will not be reached
// so no return is required here. Or, if you insist, you
// could call System.exit() and return null afterwards.
}
int fun() {
// ...
throw error();
// Again, no need for a return here, the compiler understands
// that the statement above won't return.
}
或者,也许更明确地说,您可以重构此代码以使error()
成为抛出异常的工厂:
private RuntimeException makeError() {
return new EndOfTheWorldException();
}
int fun() {
throw makeError();
}
答案 3 :(得分:1)
返回0,或者在复杂情况下,返回null。
答案 4 :(得分:1)
不确定为什么要这样做。如果你抛出一个异常,那就是更干净的代码,更可测试和可维护;您可以使用Thread.setDefaultUncaughtExceptionHandler()
退出。
但如果你坚持:
public class HaltAndCatchFireError extends Error {
public HaltAndCatchFireError() {
System.exit(1);
}
}
然后你要退出的地方:
int fun() {
...
throw new HaltAndCatchFireError();
}
答案 5 :(得分:0)
你的功能是否会返回任何东西?如果不是,你希望你的功能无效,似乎:
void fun() {
...
}
答案 6 :(得分:-2)
你可以写
error();
return;
但你可能会重新考虑你的方法。这可能不是一个非常面向对象的。