微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

java – 用于保存多个可关闭资源的类的正确习惯用法

对于用户代码,有几个选项可以正确关闭多个资源:

1.尝试资源

try (
  A a = new A();
  B b = new B();
  C c = new C()
) {
  // ...
}

除了好又短,它也是正确的.

>它将正确关闭a,b和c中的任何一个需要关闭.
>此外,它还将“抑制”在关闭期间发生的异常,如果从正文抛出异常(这是对try / finally的改进,可以在这里阅读https://docs.oracle.com/javase/tutorial/essential/exceptions/tryResourceClose.html)

2.番石榴更接近

对于JDK7之前的版本,有一个Guava的Closer,用途如下:

Closer closer = Closer.create();
try {
  A a = closer.register(new A());
  B b = closer.register(new B());
  C c = closer.register(new C());
  // ...
} catch (Throwable e) { // must catch Throwable
  throw closer.rethrow(e);
} finally {
  closer.close();
}

虽然稍微长一点,但它的效果还不错(请点击这里https://github.com/google/guava/wiki/ClosingResourcesExplained#closer获取更多信息)

拥有多个资源的对象怎么样?

我有

public class P implements AutoCloseable {
  private A a;
  private B b;
  private C c;

  public P() {
    a = new A();
    b = new B();
    c = new C();
  }

  public close() {
    c.close();
    b.close();
    a.close();
  }
}

代码存在多个问题:

>如果从构造函数抛出异常,则不会关闭任何内容(调用者没有要调用的实例关闭)
>如果从关闭引发异常,则不会关闭某些资源

1和2都没有遇到这些问题.然而:

>尝试资源显然不能使用,因为P的生命周期由调用者控制
> Guava Closer似乎也无法使用.虽然它更灵活,但它不支持close-and-rethrow,这是构造函数所必需的

没有太多样板的N资源的正确模式是什么?该解决方案还应具有1和2的抑制属性

最佳答案
您可以使用execute around方法模式从资源包装类的用户隐藏资源的打开和关闭.这样您就可以确保始终关闭资源.您应该为不同的用例添加单独的操作方法.只有当这是一个公共资源并且被应用程序的许多部分使用时,这才有用.

这是一个例子

public class ResourceWrapper {

    private A a;
    private B b;
    private C c;

    private ResourceWrapper() {
        // add try catch if you have to,after cleanup then throw exception if ithappens
        a = new A();
        b = new B();
        c = new C();
    }

    /**
     * add required operation methods
     */
    public ResourceWrapper op1() {
        // do some operations
        return this;
    }
    public ResourceWrapper op2() {
        // if additional add or different
        return this;
    }
    // close everything here
    private void close() {
        // check null if you have to
        // add try catch if you have to
        c.close();
        b.close();
        a.close();
    }

public static void use(Consumeropening and closing the resource wrapped around the operation methods by the owner of the Resource.
     *
     */
    public static void main(String[] args) {
        ResourceWrapper.use(resource->resource.op1().op2());
    }
}

原文地址:https://www.jb51.cc/java/437485.html

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐