Java 当Try块中的多行引发异常时,请使用Try With Resources,而不是finally block

Java 当Try块中的多行引发异常时,请使用Try With Resources,而不是finally block,java,exception-handling,try-catch,try-catch-finally,try-with-resources,Java,Exception Handling,Try Catch,Try Catch Finally,Try With Resources,代码段: InputStream inputStream = null; try{ ExternalServiceObject object = externalService.getObject(); inputStream = object.getInputStream(); // further uses of inputStream } catch(Exception e){ throw e; } finally { if(inputS

代码段:

InputStream inputStream = null;
try{
    ExternalServiceObject object = externalService.getObject();
    inputStream = object.getInputStream();
    // further uses of inputStream
 } catch(Exception e){
   throw e;
  } finally {
        if(inputStream != null)
           inputStream.close();
  }
在这里,externalService.getObject也可以引发异常

希望使用try with resources重构此代码,从而避免finally块。 或者当前行为是最合适的行为


非常感谢您的所有评论和回答。

可以使用try with resources块关闭InputStream。它可读性更强,不那么笨重。InputStream实现了AutoCloseable,因此在退出try with resources块时,将自动调用类的close方法。如果您只在try-catch-finally块的作用域中使用InputStream,那么应该将其移动到try块


此外,您应该尽可能避免捕获异常。在try块中引发的任何结果异常都可能导致不必要的行为

因此,如果您想使用try with resources,请使用:

try {
  ExternalServiceObject object = externalService.getObject();
  try (InputStream inputStream = object.getInputStream()) {
    // ...
  }
} catch (Exception e) {
  throw e; // But why catch it only to rethrow?
}

如果您不需要外部服务对象来执行任何其他操作:

try (InputStream inputStream = externalService.getObject().getInputStream()) {
    // further uses of inputStream
} catch (Exception e) {
    // ... logging etc
    throw e;
}

我相信try with resources中的执行顺序是自上而下的 与所有其他java变量定义一样

try
(
    ExternalServiceObject externalServiceObject = externalService.getObject(),
    InputStream inputStream = externalServiceObject.getInputStream();
)
{
    // further uses of inputStream
}
catch (Exception e)
{
    // do stuff.
}

警告:ExternalServiceObject必须实现AutoCloseable

如果您的问题是关于是否将处理在try with resources的资源声明部分中引发的异常,那么答案是肯定的。您可以用一个相对简单的例子来尝试——让您的externalService.getObject抛出一些异常,并检查是否执行了catch块。是的,这是问题的一部分。帮助我理解“尝试使用资源”。非常感谢。在try块中使用try块会不会使代码看起来有点混乱?很抱歉,在捕捉到异常之后,日志记录已经完成并记录了度量值,但是我太懒了,无法添加全部内容。非常感谢。如果这是您需要的,请看有点混乱。这段代码不会自动关闭ExternalServiceObject。@Basil也不会自动关闭OP。这个问题并没有明确说明它需要关闭。+1是极好的警告。外部服务是AWS S3Client,希望我能在这里标记它们。太好了!优雅的解决方案:“非常感谢。