java—将lambda参数传递给构造函数并在lambda中使用对象

egdjgwm8  于 2021-06-29  发布在  Java
关注(0)|答案(2)|浏览(377)

我有这样一个场景:

class ClassB{
    ClassB(){
        ClassA a = new ClassA(() -> a.foo());
    }
}

class ClassA{
    ClassA(Runnable onChange) {

    }

    public void foo(){
        System.out.println("Hello");
    }
}

我得到“变量'a'可能没有初始化”。我明白为什么会这样。有没有解决的办法或者我必须重新组织我的课程?

uidvcgyl

uidvcgyl1#

我认为你应该考虑重构你的代码并使用不同的方法。没有完整的代码很难说,但我怀疑设计不是最佳的。
说到这里,你可以做一些与你的方法相似的事情。
使classa可运行且抽象:

abstract class ClassA implements Runnable{

    private final Runnable onChange;

    protected ClassA() {
        this.onChange = this;
    }

    public void foo(){
        System.out.println("Hello");
    }
}

在classb中,可以实现匿名classa:

class ClassB {
    ClassB() {
        ClassA a = new ClassA() {
            @Override
            public void run() {
                foo();
            }
        };
    }
}
tyg4sfes

tyg4sfes2#

在不更改任何类型的情况下,这应该可以工作:

class ClassB {
    ClassB() {
        AtomicReference<A> ref = new AtomicReference<>(); // holder for instance
        ClassA a = new ClassA(() -> ref.get().foo());
        ref.set(a);
    }
}

但是你不能调用你的lambda( Runnable#run )在构造函数中,因为 a 还是有价值的 null . 只有在构造函数完成之后,才会赋值。
另一种可能是使用 Consumer 而不是 Runnable :

class ClassB {
    ClassB() {
        ClassA a = new ClassA(that -> that.foo()); // or maybe even: A::foo
    }
}

class ClassA {
    ClassA(Consumer<A> onChange) {

    }

    public void foo() {
        System.out.println("Hello");
    }
}

// call outside of `A`:
consumer.accept(a);
// or, inside of `A`:
consumer.accept(this);

如果看不到代码的其余部分,就很难给出一个好的解决方案。

相关问题