没有 catch 块的最终块是 java 反模式吗?

2022-08-31 22:42:17

我只是在对一些看起来像这样的代码进行故障排除时遇到了非常痛苦的故障排除经验:

try {
   doSomeStuff()
   doMore()
} finally {
   doSomeOtherStuff()
}

这个问题很难排除故障,因为 doSomeStuff() 抛出了一个异常,这反过来又导致 doSomeOtherStuff() 也抛出了一个异常。第二个异常(由 finally 块引发)被抛到我的代码中,但它没有处理第一个异常(从 doSomeStuff()引发),这是问题的真正根本原因。

如果代码是这样说的,那么问题就会显而易见:

try {
    doSomeStuff()
    doMore()
} catch (Exception e) {
    log.error(e);
} finally {
   doSomeOtherStuff()
}

所以,我的问题是这样的:

在没有任何 catch 块的情况下使用最终的块是众所周知的 Java 反模式吗?(它肯定是一个不容易看到的子类,显然是众所周知的反模式“不要吞噬例外!”)


答案 1

一般来说,不,这不是反模式。最后块的要点是确保无论是否引发异常,都会清理内容。异常处理的全部意义在于,如果你不能处理它,你就让它冒泡到一个可以的人身上,通过相对干净的带外信号异常处理。如果您需要确保在引发异常时清理内容,但无法在当前范围内正确处理异常,那么这正是正确的做法。你可能只是想更小心一点,以确保你的最终块不会抛出。


答案 2

我认为这里真正的“反模式”是在一个可以投掷的块中做一些事情,而不是没有接球。finally