在另一个构造函数中使用带有try-with-resources惯用法的委托构造函数

时间:2018-04-23 07:26:25

标签: java

我的课程Foo有两种构建方式:

public Foo(Bar bar)

public Foo(Baz baz)

有可能从Baz获得Bar,尝试使用资源习惯用法

try (Baz baz = bar.expensiveFunction()){
    // code here
}

我想要做的是在Foo(Bar bar)构造函数中,基本上是写

public Foo(Bar bar)
{
    try (Baz baz = bar.expensiveFunction()){
        this(baz);
    }
}

但不允许这样做,因为this(b)不在第一行。有谁知道我如何在Java中实现这一目标?当然,我可以使用initialise函数,但我宁愿不这样做。

2 个答案:

答案 0 :(得分:2)

@ Bathsheba的方法更好。但我认为在某些情况下,有一种方法只适用于构造函数。

如果Foo类扩展Object,您可以执行此操作:

public Foo(Bar bar) {
    this(bar.expensiveFunction(), true);
}

public Foo(Baz baz) {
    this(baz, false);
}

private Foo(Baz baz, boolean close) {
    super();
    try {
       // initialize
    } finally {
        if (close) {
            baz.close();
        }
    }
}

如果new Foo(someBar)Foo对象的初始分配中抛出OOME,则会在调用expensiveFunction()之前发生,因此不会BazFoo关闭。

但如果super()扩展了其他一些类,那么Foo(Baz, boolean) 中的Foo调用可以抛出异常...... 不能Baz捕获。如果您无法捕获异常,则无法关闭 There can only be one CMD instruction in a Dockerfile. If you list more than one CMD then only the last CMD will take effect.

答案 1 :(得分:1)

避免initialize函数(例如,这意味着字段不能final)的一种替代方案是重构更多的“昂贵”#34 ;函数转换为static

public static Foo makeFoo(Bar bar){
    try (Baz baz = bar.expensiveFunction()){
        return new Foo(baz);
    }
}

应该在呼叫站点提供最小的污染。