我试图更好地理解方法引用是如何工作的。在这个例子中,我遵循了代码的逻辑,但我不明白这样做的价值。基本上,在 STEP 2 中的方法引用赋值之后,someMethod() 被用作 MyInterface 的 display() 抽象方法的实现。但为什么呢?这样做我们得到了什么?这在架构上什么时候有意义?好像我们把与类无关的Interface和这个赋值关联起来。
@FunctionalInterface
interface MyInterface {
void display();
}
class DerivClass {
public void someMethod(){
System.out.println("Derived class method");
}
}
public class RefTest {
public static void main(String[] args) {
DerivClass dc = new DerivClass(); // STEP1: class instance
MyInterface myInterf = dc::someMethod; // STEP 2: assign method ref to interface
myInterf.display(); // STEP 3: executes someMethod(), prints "Derived class method"
}
}
Run Code Online (Sandbox Code Playgroud)
您开始了解方法参考的好地方是Oracle 文档,它说:
您可以使用 lambda 表达式来创建匿名方法。然而,有时 lambda 表达式除了调用现有方法之外什么都不做。在这些情况下,按名称引用现有方法通常会更清楚。方法引用使您能够做到这一点;它们是用于已具有名称的方法的紧凑、易于阅读的 lambda 表达式。
可以这样想:
"方法定义(特定的主体、签名和返回类型)存在;如果我可以重用现有代码,为什么还要创建新的 lambda 表达式?让我们参考已经定义的方法并重用它。 “
SomeType::staticMethodName - 引用静态方法(你只是引用“SomeType”类的静态方法);
someTypeInstance::instanceMethodName- 对特定对象的实例方法的引用(这里,您需要一个实际对象,从中获取方法引用);
SomeType::instanceMethod - 引用特定类型的任意对象的实例方法(在这种情况下,您不需要显式创建对象);
SomeType::new - 对构造函数的引用(您只需引用构造函数)。
(2) 特定对象的方法引用和 (3) 任意对象的方法引用之间的区别:
在前两个示例中,方法引用等效于提供方法参数的lambda 表达式。例如:
System.out::println == x -> System.out.println(x);
Math::pow == (x, y) -> Math.pow(x, y)
Run Code Online (Sandbox Code Playgroud)
在第三种情况下,第一个参数成为方法的目标,如下所示:
String::compareToIgnoreCase == (x, y) -> x.compareToIgnoreCase(y)
Run Code Online (Sandbox Code Playgroud)