异常和错误的区别

我正在学习更多关于基本Java和不同类型的Throwables,有人能让我知道异常和错误之间的区别吗?

101677 次浏览

错误不应该被捕获或处理(除非在最罕见的情况下)。异常是异常处理的基础。Javadoc很好地解释了它:

一个Error是Throwable的子类,它指示了一个严重的问题 合理应用不宜试图抓。大多数这样的错误是不正常的 条件。< / p >

看看Error的几个子类,它们有一些JavaDoc注释:

  • AnnotationFormatError -当注释解析器试图从类文件中读取注释并确定该注释格式不正确时抛出。
  • AssertionError -抛出,表示断言失败。
  • LinkageError - LinkageError的子类表明一个类依赖于另一个类;但是,在编译前一个类之后,后一个类发生了不兼容的变化。
  • VirtualMachineError -抛出,表示Java虚拟机损坏或耗尽了继续运行所需的资源。

Throwable实际上有三个重要的子类别:

  • Error -一些足够严重的错误,大多数应用程序应该崩溃,而不是试图处理这个问题,
  • 未检查异常(又名RuntimeException) -通常是一个编程错误,例如NullPointerException或非法参数。应用程序有时可以处理或从这个Throwable类别中恢复——或者至少在线程的run()方法中捕获它,记录投诉,并继续运行。
  • Checked Exception(又名Everything else)——应用程序被期望能够捕获并对其余的异常做一些有意义的事情,例如FileNotFoundExceptionTimeoutException

如您所知,错误往往标志着应用程序的结束。它通常无法恢复,并且会导致虚拟机退出。除非在退出前可能记录或显示适当的消息,否则不应该捕获它们。

< p > < >强的例子: OutOfMemoryError -你不能做什么,因为你的程序不能再运行了

异常通常是可恢复的,即使不可恢复,它们通常只是意味着尝试的操作失败了,但您的程序仍然可以继续进行。

< p > < >强的例子:

. IllegalArgumentException -将无效数据传递给方法,使方法调用失败,但不影响后续操作

这些都是简单的例子,还有大量关于异常的信息。

太阳说得最好:

Error是Throwable的子类 这表明存在严重的问题 合理应用不宜尝试 赶上。< / p >

Error类的描述非常清楚:

ErrorThrowable的子类 这表明存在严重的问题 合理应用不宜尝试 赶上。大多数这样的错误是 异常条件。的ThreadDeath 错误,虽然是一个“正常”的条件,是 也是Error的子类,因为大多数 应用程序不应该试图捕获 它。< / p >

一个方法不需要声明 的任何子类抛出子句 类过程中可能抛出的Error 方法的执行,但不是 捕获,因为这些错误是 不正常的情况不应该发生 发生。< / p >

引用自Java自己的Error的文档

简而言之,你不应该捕获Errors,除非你有一个很好的理由这样做。(例如,防止您的web服务器的实现崩溃,如果servlet运行到内存或类似的东西。)

另一方面,Exception只是一个正常的异常,就像任何其他现代语言一样。您可以在Java API文档或任何在线或离线资源中找到详细的描述。

下面是Java API中关于错误和异常的一个很好的总结:

Error是Throwable的子类,它指示了一个合理的应用程序不应该尝试捕捉的严重问题。大多数这样的错误是不正常的情况。ThreadDeath错误虽然是“正常”的情况,但也是error的子类,因为大多数应用程序不应该尝试捕获它。

一个方法不需要声明 的任何子类抛出子句 处理过程中可能引发的错误 方法的执行,但不是 捕获,因为这些错误是 不正常的情况不应该发生 发生。< / p >

OTOH,对于异常,Java API说:

Exception类及其子类是Throwable的一种形式,表示合理的应用程序可能想要捕获的条件。

在我看来,错误会导致你的应用程序失败,不应该被处理。异常可能导致不可预知的结果,但可以从中恢复。

例子:

如果一个程序已经耗尽内存,这是一个错误,因为应用程序不能继续。但是,如果程序接受了错误的输入类型,则属于例外,因为程序可以处理它并重定向到接收正确的输入类型。

错误主要是由应用程序运行的环境引起的。例如,当JVM内存耗尽时会发生OutOfMemoryError,当堆栈溢出时会发生StackOverflowError。

异常主要是由应用程序本身引起的。例如,当应用程序试图访问空对象时,会发生NullPointerException;当应用程序试图强制转换不兼容的类类型时,会发生ClassCastException。

来源:Java中错误和异常的区别

java.lang.Exception和类java.lang.Error之间有一些相似和不同之处。

相似之处:

    第一个-两个类都扩展了java.lang.Throwable和作为结果 继承在处理时常用的许多方法 错误包括:getMessagegetStackTraceprintStackTrace和 李。< / p > < / > 其次,作为java.lang.Throwable的子类,它们都继承了 以下属性:< / p >
    • Throwable本身及其任何子类(包括java.lang.Error)可以使用throws关键字在方法异常列表中声明。只有java.lang.Exception及其子类需要这样的声明,而对于java.lang.Throwablejava.lang.Errorjava.lang.RuntimeException及其子类则是可选的。

    • catch子句中只允许使用java.lang.Throwable及其子类。

    • 只有java.lang.Throwable和子类可以与关键字- throw一起使用。

    • 李< / ul > < / >

    这个属性的结论是java.lang.Errorjava.lang.Exception都可以在方法头中声明,可以在catch子句中,可以与关键字throw一起使用。

    差异:

    • 第一个概念差异:java.lang.Error设计为 JVM抛出,表明问题严重,并打算停止 程序执行而不是被捕获(但它是可能的 任何其他java.lang.Throwable继承者)。< / p >

      javadoc中关于java.lang.Error的描述:

      < p >…表示合理的应用程序应该出现的严重问题

      在相反的java.lang.Exception中,设计用于表示错误 程序员可以在不终止的情况下处理它 程序执行。< / p >

      javadoc中关于java.lang.Exception的描述:

      < p >…指示合理的应用程序可能需要的条件 抓住。< / p > 李< /引用> < / >
    • java.lang.Errorjava.lang.Exception之间的第二个区别首先被认为是用于编译时异常检查的无节制的异常。作为结果,抛出java.lang.Error或其子类的代码不需要在方法头中声明此错误。在方法头中抛出java.lang.Exception required声明时。

    Throwable及其后续类图(属性和方法省略)。 enter image description here < / p >

这个幻灯片展示了Java的异常层次结构 by @georgios-gousios简洁地解释了Java中错误和异常之间的区别。

Java Exception Hierarchy

Errors -

  1. java中的__abc0类型为java.lang.Error
  2. java中的所有错误都是未检查的类型。
  3. __abc发生在运行时。它们不会被编译器知道。
  4. 从错误中恢复是不可能的。
  5. __abc0主要是由应用程序运行的环境引起的。
  6. __abc2 __abc0, __abc1

异常 -

  1. java中的__abc0类型为java.lang.Exception
  2. Exceptions既包括checked类型,也包括unchecked类型。
  3. 编译器知道已检查异常,而编译器不知道未检查异常,因为它们发生在运行时。
  4. 你可以通过try-catch块处理异常来恢复。
  5. __abc0主要是由应用程序本身引起的。
  6. 例子:已检查异常:SQLExceptionIOException
    . 未检查异常:ArrayIndexOutOfBoundExceptionClassCastExceptionNullPointerException

进一步阅读:http://javaconceptoftheday.com/difference-between-error-vs-exception-in-java/ http://javaconceptoftheday.com/wp-content/uploads/2015/04/ErrorVsException.png < / p >

错误是由应用程序或程序运行的环境引起的。大多数情况下,您可能无法从中恢复,因为这会结束您的应用程序或程序。Javadoc建议你不应该费心去捕捉这样的错误,因为环境(例如JVM)在这样的错误上无论如何都会退出。

< p >例子: VirtualMachineError -抛出,表示Java虚拟机损坏或耗尽了继续运行所需的资源。 OutOfMemoryError发生在JVM内存不足或

. StackOverflowError当堆栈运行超过时发生

异常是由您的应用程序或程序本身引起的;也许是因为你自己的错误。大多数情况下,您可以从中恢复,应用程序仍将继续运行。建议您捕捉此类错误,以防止应用程序或程序异常终止,并且/或能够自定义异常消息,以便用户看到格式化良好的消息,而不是分散在各处的缺省丑陋异常消息。

< p >例子: 当应用程序试图访问空对象时发生NullPointerException。或 试图访问一个索引不存在的数组,或者使用错误的数据或参数调用函数