开发者

performing clean up and passing the exception to the caller

开发者 https://www.devze.com 2023-02-07 04:00 出处:网络
I need to do some initialization and clean it up in case of any exception. I\'d still like the exception to be passed to the caller. The problem is I now have to declare this method as throws Throwabl

I need to do some initialization and clean it up in case of any exception. I'd still like the exception to be passed to the caller. The problem is I now have to declare this method as throws Throwable and then I have to explicitly handle this throwable in the caller, just as if开发者_StackOverflow all procedures don't throw Throwables implicitly already. Stupid isn't it?


try {
  init_step1();
  init_step2();
}
catch (Throwable th) {
  clean();
  throw th;
}


One way of doing this is to perform the cleanup in a finally block instead, noticing whether there's been an exception by whether you actually got to the end of the try block or not:

boolean success = false;
try {
    // Stuff here
    success = true;
} finally {
    if (!success) {
        clean();
    }
}


Stupid is fighting against checked exceptions. You have to throw something different if you don't want to require every caller to handle it. just throw a RuntimeException

public void myMethod() throws RuntimeException {
    try {
      init_step1();
      init_step2();
    }
    catch (Throwable th) {
        clean();
        throw new RuntimeException(th);
    }
}

why do you catch Throwable in first place anyway? init_step1() and init_step2() doesn't throw an exception?


@Jon Skeet's solution is the cleanest. Another solution which may interest you.

try {
    // Stuff here
} catch(Throwable t) {
    clean(t);
    // bypasses the compiler check
    Thread.currentThread().stop(t); 
}

I would only suggest using this approach if you needed to know the exception thrown. e.g. For resources I have which are closable, I record the exception which triggered their close. This way if I try to use the resource and it is closed I can see why it is closed.

private void checkClosed() {
    if (closed)
        throw new IllegalStateException("Closed", reasonClosed);
}
0

精彩评论

暂无评论...
验证码 换一张
取 消