Java 什么时候应该使用Throwable而不是new Exception?

Java 什么时候应该使用Throwable而不是new Exception?,java,exception,throwable,Java,Exception,Throwable,给定:Throwable是Exception的超类 当我阅读关于编写您自己的“异常”的文本时,我看到catch块中使用了Throwable的示例,其他文本显示new Exception()在catch块中使用。我还没有看到关于何时应该使用每种方法的解释 我的问题是,什么时候应该使用Throwable,什么时候应该使用newexception() 在catch或else块内,使用以下任一方法: throw throwable; 或 始终抛出一个异常(永远不要抛出一个可丢弃的)。通常情况下,您也不

给定:
Throwable
Exception
的超类

当我阅读关于编写您自己的“异常”的文本时,我看到
catch
块中使用了
Throwable
的示例,其他文本显示
new Exception()
catch
块中使用。我还没有看到关于何时应该使用每种方法的解释

我的问题是,什么时候应该使用
Throwable
,什么时候应该使用
newexception()

catch
else
块内,使用以下任一方法:

throw throwable;


始终抛出一个
异常
(永远不要抛出一个
可丢弃的
)。通常情况下,您也不会捕获可丢弃的
,但您可以。Throwable是
异常
错误
的超类,因此,如果您不仅想捕获
异常
而且想捕获
错误
的话,您可以捕获
Throwable
,这就是拥有它的意义所在。问题是,
Error
s通常是普通应用程序不会也不应该捕获的东西,所以只要使用
Exception
,除非您有特定的理由使用
Throwable

Throwable是一个接口,而不是一个类。两个类扩展了Throwable,Exception和Error

规则是:捕获异常时尽可能具体-这意味着,例如捕获异常而不是可丢弃的,以及IOException而不是异常

不要捕捉错误-错误是错误。改为修复代码


如果您必须捕获所有内容,请使用“catch-Throwable”,但这是一种糟糕的形式。

您不应该真正捕获异常并抛出一个与“new-exception”一样通用的新异常

相反,如果希望冒泡出现异常,只需执行以下操作:

try {
    // Do some stuff here
}
catch (DivideByZeroException e) {
    System.out.println("Can't divide by Zero!"); 
} 
catch (IndexOutOfRangeException e) { 
    // catch the exception 
    System.out.println("No matching element found.");
}
catch (Throwable e) {
    throw e; // rethrow the exception/error that occurred
}

我认为,捕获异常并抛出新异常(而不是引发到代码块中的异常)并不是一种好的做法,除非您提出了一个有用的自定义异常,该异常提供了足够的上下文,可以避开原始异常的原因。

正如我在java首次出现时听到的那样,该理论认为,除了例外情况外,在其他情况下,可抛弃性也可用于控制权的转让。我从来没有见过这样使用它(这可能是一件非常好的事情)


所以只捕获异常(或者更好的是,更细粒度的异常)。

Throwable意味着只被程序的容器或主循环捕获。大多数情况下,捕捉异常(例如错误)下面的内容并不会给程序增加太多功能,毕竟,如果抛出VirtualError或其他错误,您可以做些什么呢。除了记录并继续之外,没有什么

(来自评论)提出这一点的问题是 我需要将“异常”传递给 一个同事正在构建的代码 如果未生成集合

在这种情况下,您可能希望抛出一个选中的异常。您可以抛出一个、一个适当的现有子类(及其未选中的子类除外)或一个自定义的
Exception
(例如“
CollectionBuildException
”)子类。请参阅以了解Java异常的最新情况。

抛出新异常()是您在catch块中永远不应该执行的操作,但您可能必须或想要执行throw
newsomeexception(throwable)
(保留完整的堆栈跟踪)而不是
抛出可丢弃
以符合方法的API,例如,当它声明抛出
SomeException
时,但您调用的代码可能抛出一个
IOException
,您不想将其添加到方法的
throws
子句中


最常见的情况可能是
newruntimeexception(throwable)
以避免出现
抛出
子句。许多人会告诉你这是一种可怕的滥用,因为你应该使用检查异常。在我看来,它们是错误的,检查异常是Java语言设计中的一个错误,只会导致丑陋的、不可维护的代码。

所有异常最终都是一个问题。。。也有人说错误是错误,但这并不意味着什么


错误不是bug-它们是主机VM遇到的问题,例如OutOfMemoryError。异常是当前操作可以用来通知它失败的一种方法,并可能提供一些诊断。

通常,您不会抛出或捕获可丢弃的。特别是,JVM错误(扩展Error())并不意味着被用户代码捕获,除非您正在执行奇怪的系统级工作

将“可丢弃”视为语言制品。“Exception”类之所以这样命名,是因为当程序员希望代码块“异常地”退出(不正常退出或返回值)时,可以使用它


这既包括常规错误情况(我所说的“常规”是指与JVM错误相反的情况),也包括将异常用作控制机制的情况。

您也不应该将异常用作“返回类型”

如果您抛出的条件很常见,那么您将花费大量资源将该条件返回到调用例程。构造异常非常昂贵


我见过这样的情况:紧密循环将异常作为ID分配的“负面”抛出,该例程占用了大约99%的CPU时间。。当改为记录的返回常数时,该值下降到25%。

在代码中只有两个地方可以看到单词
Throwable

public static void main(String args[])
{
     try
     {
         // Do some stuff
     }
     catch(Throwable t)
     {

     }
 }


甲骨文给出了答案

首先,它解释了
Throwables
错误
异常
类的联合体,它们是两个不同的事物

接下来,它明确指出,
错误
是极其罕见的,几乎不可能从中恢复。
public static void main(String args[])
{
     try
     {
         // Do some stuff
     }
     catch(Throwable t)
     {

     }
 }
public class SomeServlet extends HttpServlet
{
      public void doPost(HttpRequest request, HttpResponse response)
      {
         try
         {
             // Do some stuff
         }
         catch (Throwable t)
         {
              // Log
         }
      }
 }