为什么“使用资源试用”捕获块是选择性可选的?

2022-09-01 10:59:13

我读到“尝试资源”中的块是可选的。我尝试过在资源试用块中创建一个对象,没有后续块,只是从eclipse获得编译器错误:“自动调用引发的未处理的异常类型。catchConnectioncatchSQLExceptionclose()

由于可以在 try-with-resources 中使用的每个资源都实现了 ,因此在调用该方法时可能会引发异常,因此我不明白该子句是如何可选的,因为它不允许我跳过从 中捕获异常。AutoCloseableclose()catchclose()

是否有一些特殊要求,即不直接声明在其方法中抛出的任何异常?(例如,用不抛出任何异常的覆盖 's)?AutoCloseableclose()AutoCloseableclose() throws Exceptionclose()

..或者这可能只是一个日食问题?

编辑:这是仍然触发问题的最简单的代码片段:

try (Connection con = dataSource.getConnection()) {
  /*...*/

}

关于这是否与使用JNDI数据源有关的想法?

提前致谢。


答案 1

如果 无法引发已检查的异常,则它是可选的。但是,如果可以,则需要以正常方式处理已检验的异常,使用块或从该块所在的方法引发。close()close()catchtry-with-resources

有关更多详细信息,请参阅 JLS 14.2.3

14.20.3.2. 扩展的资源试用

具有至少一个 catch 子句和/或 finally 子句的 try-with-resources 语句称为扩展的 try-with-resources 语句。

扩展的资源试用语句的含义:

try ResourceSpecification
    Block
[Catches]
[Finally]

通过以下翻译给出嵌套在 try-catch 或 try-finally 或 try-catch-finally 语句中的基本 try-with-resources 语句:

try {
    try ResourceSpecification
       Block
}
[Catches]
[Finally]

转换的效果是将资源规范放在 try 语句的“内部”。这允许扩展的资源试用语句的 catch 子句捕获由于任何资源的自动初始化或关闭而导致的异常。

此外,在执行 finally 块时,所有资源都将被关闭(或试图关闭),这与 finally 关键字的意图一致。

关于这是否与使用JNDI数据源有关的想法?

是的,它是。

在你提供的示例 try-with-resourses 块中,有必要捕获异常并处理,或者从该块所在的方法中引发,因为这是一个已检查的异常。SQLException


答案 2

您可能只是抛出异常(或在另一个 try-catch 块中捕获它):

private static void test() throws IOException {
    try(InputStream is = new FileInputStream("test.txt")) {
        while(is.read() > -1) {
        }
    } finally {
        // Will get executed, even if exception occurs
        System.out.println("Finished");
    }
}

推荐