由于 Java lambda 表达式实际上就是方法,因此 lambda 表达式可以像方法一样接受参数。前面所示的 lambda 表达式的 (oldState, newState) 部分指定了 lambda 表达式所接受的参数。这些参数必须与单方法接口上的方法参数相匹配。在本例中,这些参数必须与 StateChangeListener 接口的 onStateChange() 方法的参数相匹配:
public void onStateChange(State oldState, State newState);
至少,lambda 表达式和方法中的参数数量必须匹配。
其次,如果在 lambda 表达式中指定了参数类型,这些类型也必须匹配。我还没有向你演示如何在 lambda 表达式的参数上添加类型(本文稍后会演示),但在很多情况下,你并不需要它们。
如果与 lambda 表达式匹配的方法不带参数,那么可以这样编写 lambda 表达式:
() -> System.out.println("Zero parameter lambda");
注意:括号中间没有内容。这表示 lambda 不带参数。
如果与您的 Java lambda 表达式匹配的方法只有一个参数,您可以这样编写 lambda 表达式:
(param) -> System.out.println("One parameter: " + param);
注意:参数列在括号内。
当 lambda 表达式只接受一个参数时,也可以省略括号,就像下面这样:
param -> System.out.println("One parameter: " + param);
如果与您的 Java lambda 表达式匹配的方法需要多个参数,则需要在括号内列出这些参数。下面是 Java 代码中的示例:
(p1, p2) -> System.out.println("Multiple parameters: " + p1 + ", " + p2);
注意:只有当方法只接受一个参数时,才可以省略括号。
如果编译器无法从 lambda 所匹配的函数接口方法中推断出参数类型,那么有时就有必要为 lambda 表达式指定参数类型。别担心,编译器会告诉您何时需要这样做。下面是一个 Java lambda 参数类型示例:
(Car car) -> System.out.println("The car is: " + car.getName());
正如你所看到的,car 参数的类型(Car)被写在了参数名的前面,就像在其他地方的方法中声明参数时,或者在匿名实现接口时一样。
从 Java 11 开始,您可以使用 var 关键字作为参数类型。var 关键字是在 Java 10 中作为局部变量类型推断引入的。从 Java 11 开始,var 也可用于 lambda 参数类型。下面是一个在 lambda 表达式中使用 var 关键字作为参数类型的示例:
Function<String, String> toLowerCase = (var input) -> input.toLowerCase();
使用上述 var 关键字声明的参数类型将被推断为 String 类型,因为变量类型声明的泛型类型设置为 Function<String,String>,这意味着 Function 的参数类型和返回类型均为 String。