有没有办法将现有界面变成功能界面?

Jaz*_*zer 9 java lambda java-8 functional-interface

我使用的界面看起来像这样:

public interface ObjectListener {
    public void objectAdded(Object o);
    public void objectRemoved(Object o);
}
Run Code Online (Sandbox Code Playgroud)

我目前正在使用匿名类来实现接口,但我不关心这两种方法中的一种.有点像这样:

someObject.addListener(new ObjectListener() {

    @Override
    public void objectAdded(Object o) {
        doSomething(o);
    }

    @Override
    public void objectRemoved(Object o) {}
});
Run Code Online (Sandbox Code Playgroud)

现在,无论我在哪里,我都在Java 8中使用新的lambda表达式,并且我希望在这种情况下使用增加的简单性.毕竟,我只是实现了其中一个方法,但由于接口中有两个方法,我不能在lambda表达式中使用它.

有没有办法解决这个限制?

Jaz*_*zer 9

为了重用lambda表达式中不是函数接口的现有接口,还必须使用新的Java8功能,即默认方法.

在这种情况下,如果您想使用lambda表达式代替匿名类,则必须执行以下操作.

首先,您需要将ObjectListener重新定义为新接口:

public interface ObjectAddedListener extends ObjectListener {
    @Override
    default public void objectRemoved(Object o) {}
}
Run Code Online (Sandbox Code Playgroud)

我们只是简单地向我们不关心的方法添加一个空的默认实现,这使得该objectAdded()方法成为接口中唯一的抽象方法.

然后您可以使用新类型代替任何ObjectListener,并且由于在新接口中只有一个没有实现的方法,您可以在lambda表达式中使用它,如下所示:

ObjectAddedListener listener = o -> doSomething(o);
someObject.addListener(listener);
Run Code Online (Sandbox Code Playgroud)

请注意,如果要在addListener()方法中直接使用此新类型,首先需要将lambda表达式转换为新定义的类型,如下所示:

someObject.addListener((ObjectAddedListener) o -> doSomething(o));
Run Code Online (Sandbox Code Playgroud)