try-with-resource中的close()异常

时间:2013-12-18 12:04:20

标签: java java-7 try-with-resources

我正在阅读JDK7中的try-with-resource,当我考虑升级我的应用程序以运行JDK7时,我遇到了这个问题..

当使用BufferedReader时,例如写入抛出IOException并且close抛出IOException ..在catch块中我关注写入抛出的IOException ...但我不会太在意关闭抛出的那个..

数据库连接和任何其他资源的相同问题..

作为一个例子,我创建了一个自动关闭资源:

public class AutoCloseableExample implements AutoCloseable {

    public AutoCloseableExample() throws IOException{
        throw new IOException();
    }

    @Override
    public void close() throws IOException {
        throw new IOException("An Exception During Close");
    }

}

现在使用它时:

public class AutoCloseTest {

    public static void main(String[] args) throws Exception {
        try (AutoCloseableExample example = new AutoCloseableExample()) {
            System.out.println(example);

            throw new IOException("An Exception During Read");
        } catch (Exception x) {
            System.out.println(x.getMessage());
        } 
    }

}

如何在不必为BufferedReader等类创建包装器的情况下区分这些异常?

大多数情况下,我将资源关闭在finally块中的try / catch中,而不关心处理它。

2 个答案:

答案 0 :(得分:12)

让我们考虑一下这个课程:

public class Resource implements AutoCloseable {

    public Resource() throws Exception {
        throw new Exception("Exception from constructor");
    }

    public void doSomething() throws Exception {
        throw new Exception("Exception from method");
    }

    @Override
    public void close() throws Exception {
        throw new Exception("Exception from closeable");
    }
}

和try-with-resource块:

    try(Resource r = new Resource()) {
        r.doSomething();
    } catch (Exception ex) {
        ex.printStackTrace();
    }

1。启用所有3个抛出语句。

将打印消息“构造函数的异常”,构造函数抛出的异常将被抑制,这意味着您无法捕获它。

2。删除了构造函数。

现在堆栈跟踪将在下面打印“Exception from method”和“Suppressed:Exception from closeable”。在这里你也无法捕获close方法抛出的被抑制异常,但你将被禁止有关被抑制的异常。

3. 将删除构造函数和方法的抛出。

正如您可能已经猜到的那样,“可以关闭的例外情况”将被打印出来。

重要提示:在上述所有情况下,您实际上捕获所有异常,无论他们被扔到哪里。因此,如果你使用try-with-resource块,你不需要用另一个try-catch包装块,它就没用了。

希望有所帮助:)

答案 1 :(得分:0)

我建议使用以下示例中的标志:

static String getData() throws IOException {
    boolean isTryCompleted = false;
    String theData = null;
    try (MyResource br = new MyResource();) {

        theData = br.getData();
        isTryCompleted = true;

    } catch(IOException e) {
        if (!isTryCompleted )
            throw e;
        // else it's a close exception and it can be ignored
    }

    return theData;
}
  

源:Close resource quietly using try-with-resources