我们可以在java中包含一个自己的Exception

时间:2012-10-03 04:13:02

标签: java exception exception-handling

我可以创建像

这样的例外
A a = new A (new B ( new A ) );

其中AB是两种不同类型的例外。

我知道Java可以做到但这样做是对的吗?

编辑:我正在编写一个Exception类型的重试,所以我正在检查Exception的getCause。当getCause为null或getCause等于我自己时,我正在断开,当getCause等于到目前为止看到的任何异常时,我是否也应该中断

3 个答案:

答案 0 :(得分:4)

  

AException a = new AException(new BException(new AException));

这是合法的。


您也可以使用initCause(Throwable)方法直接初始化原因。

如果你试图将异常作为自己的原因; e.g。

 AException a = new AException();
 a.initCause(a);

您将获得IllegalArgumentException("Self-causation not permitted")。 (感谢Joachim Sauer指出这一点。)

虽然,JVM不会阻止你创建一个间接周期,但它仍然是一个非常糟糕的主意

  • 滥用Throwable API。对于特殊事件直接或间接导致其自身没有逻辑意义。

  • 可能存在假定的代码,异常的“原因”链没有任何循环。如果它遇到具有原因周期的病态异常,则这种代码很可能以令人讨厌的方式失败。

请注意,当前生成(Java 7)printStackTrace()检测并处理“原因”周期,但前几代没有:

答案 1 :(得分:1)

考虑你有以下课程。

public static class A extends Exception {
    public A() {}
    public A(Exception e) {}

}
public static class B extends Exception {
    public B(Exception e) {}
    public B() {}
}

现在,如果您看到在默认构造函数中出现时总是以包装异常结束。在此之前,您应该致电getCause()

 throw new B(new A(new B()));//Ends with B since no exception is wrapped inside it.

答案 2 :(得分:1)

这需要三个略有不同的答案:

  1. ,您可以将异常包装在相同类型的另一个例外中。

  2. ,您无法在本身中包装异常(例如,在完全相同的实例中)。

  3. 不幸的是,您可以创建一个循环(导致B的A导致A导致B ...)。

  4. 第一个非常清楚:你可以用IllegalStateException包裹由另一个IllegalArgumentException引起的IllegalStateException

    第二个被initClause()中的代码阻止(由构造函数调用,或者如果以前从未调用过,可以直接调用),这会阻止自我因果关系(实际上cause == this是用作未设置原因的标志,以区别于cause == null,这意味着原因明确设置为null)。

    第三点是不好的,但在实践中不应经常发生,因为你必须做一些额外的工作才能得到它:

    Exception e1 = new Exception();
    Exception e2 = new Exception(e1);
    e1.initCause(e2);
    

    幸运的是printStackTrace()实际处理了这种情况:

    java.lang.Exception: java.lang.Exception
        at ScratchMain.main(ScratchMain.java:6)
    Caused by: java.lang.Exception
        at ScratchMain.main(ScratchMain.java:5)
        [CIRCULAR REFERENCE:java.lang.Exception: java.lang.Exception]