繁体   English   中英

Java中的致命异常处理

[英]Fatal exception handling in Java

我正在用Java创建一个基本的数学解析器,这样做揭示了我对Java异常处理的浅薄理解。

当我有这个输入:

String mathExpression = "(3+5";

然后我打电话给:

throw new MissingRightParenException();

IDE强制我用try / catch包围,如下所示:

             try {
                    throw new MissingRightParenException();
                } catch (MissingRightParenException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();

                }

但是,为了强制这是一个致命的异常,看起来我必须添加自己的代码来调用System.exit() ,如下所示:

             try {
                    throw new MissingRightParenException();
                } catch (MissingRightParenException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                    System.exit(0);
                }

我不确定我是否理解所有这些背后的语法,特别是为什么我必须使用try / catch块来抛出异常。

这背后的押韵和原因是什么?

而不是抛出异常,我可以这样做:

new MissingRightParenException();

而不是打电话

throw new MissingRightParenException();

所以我想我的问题是 - 如果这是一个致命的例外,那么在给用户提供最佳反馈的同时让它真正致命的最佳方法是什么?

如果你想要一个必须捕获的检查异常 - 但不是马上 - 那么你可以在方法的签名中定义throws MissingRightParenException

class MissingRightParenException extends CalculationException {
    ...
}

class CalculationException extends Exception {
    ...
}

class MyClass {

    int myMathRelatedMethod(String calculation) throws CalculationException {
        ...
        if (somethingWrong) {
            throw new MissingRightParenException("Missing right paren for left paren at location: " + location);
        }
        ...
    }

    public static void main(String ... args) {        
        ...
        try {
            myMathRelatedMethod(args[0]);
        } catch (CalculationException e) {
            // stack trace not needed maybe
            System.err.println(e.getMessage());
        }
        ...
    }
}

您也可以将其定义为RuntimeException原因 ,但这似乎不适合您当前的问题。

try {
     ...
     throw new MissingRightParenException();
     ...
} catch (MissingRightParenException e) {
     // IllegalStateException extends (IS_A) RuntimeException
     throw new IllegalStateException("This should never happen", e);
}

如果您的MissingRightParenException类扩展了RuntimeException那么您不必捕获它。 该消息将落在所有方法中(或者它的父类如ThrowableExceptionRuntimeException )未被显式捕获。 但是,您不应将RuntimeException用于与输入相关的错误。

通常,用户将获得堆栈跟踪或至少是错误消息,尽管这当然取决于线路上的错误处理。 请注意,即使main也不必处理异常。 您可以为main方法指定throws Exception ,让控制台接收堆栈跟踪。

所以最后:在你想要处理它们之前,使用throws方法的签名而不是捕获异常。

假设您的异常当前是Exception的子类,这是一个Checked Exception,您需要在try catch中处理。 如果你可以使你的异常成为RunTimeException,你不再需要做try-catch的东西。

在为用户提供最佳反馈的同时,让它真正致命的最佳方法是什么?

就个人而言,我认为缺少的括号应该是致命的例外。 用户应该有可能重新尝试。

但是,如果你真的想知道,用java创建自定义致命异常是不可能的,因为致命异常意味着系统/ jvm出错了,而不是程序本身。 仍然,您应该将System.exit(0)更改为System.exit(1)或任何不等于0的程序作为退出0的程序,因为错误代码表示一切正常,这不是异常的定义。

我不确定我理解所有这些背后的语法

基本上你在这里做的是抛出一个异常,所以你有两个选择,要么抓住它,要么重新抛出它,但无论如何它必须被捕获到某个地方。 然后在catch你只是结束程序返回一个错误代码,意味着某些东西失败了System.exit(1)

在系统中看到这种差异。 Java中的exit(0),System.exit(-1),System.exit(1),以便更好地理解错误代码。

如果MissingRightParenException是一个已检查的异常(似乎是这种情况,否则你的IDE不会“唠叨”),那么要么必须将它包装在try ... catch块中,要么通过方法中的throws子句声明它定义。 后者允许你“冒泡”异常并捕获抛出MissingRightParenException异常的方法的调用者。

你有没有想过throws条款?

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM