一、方法引用
方法引用 当Lambda体中内容的方法已经实现,我们可以使用“方法引用” (可以理解为方法引用是Lambda表达式的另一种表现形式)
方法引用:使用操作符 “::” 将方法名和对象或类的名字分隔开来。 如下三种主要使用情况:
对象::实例方法
类::静态方法
类::实例方法
使用方法引用的注意事项:
1、Lambda体中调用方法的参数列表与返回值类型,要与函数式接口中抽象方法得函数列表和返回值类型保持一致。
2、若Lambda参数列表中的第一参数是实例方法的调用者,而第二各参数是实例方法的参数时,可以使用ClassName::method
实例1:对象::实例方法
@Test
public void test1() {
//如果在方法体中,已经有方法完成该功能的实现,那么就可以使用方法引用代替Lambda表达式
PrintStream ps = System.out;
Consumer<String> con = (x) -> ps.println(x);
PrintStream ps1 = System.out;
Consumer<String> con1 = ps1::println;
Consumer<String> con2 = System.out::println;
con2.accept("Hello JAVA");
}
@Test
public void test2() {
Employee emp = new Employee("zhangsan", 18, 10000);
Supplier<String> sup = () -> emp.getName();
String name = sup.get();
System.out.println(name);
System.out.println("----------------");
Supplier<String> sup1 = emp::getName;
String name1 = sup.get();
System.out.println(name1);
}
根据注意事项一,
Consumer<T>接口中的抽象方法 void accept(T t); 与PrintStream类中的void println(String x)的方法参数列表和返回值一致
Supplier<T>接口中的抽象方法 T get(); 与我们创建的Employee类中的String getName() 方法 参数列表和返回值一致
实例2:类::静态方法名
实现两个数值的比较
@Test
public void test3() {
Comparator<Integer> com = (x, y) -> Integer.compare(x, y);
Comparator<Integer> com1 = Integer::compare;
}
实例3:对象::实例方法名
判断两个字符串是否相同
@Test
public void test4() {
BiPredicate<String, String> bp = (x, y) -> x.equals(y);
BiPredicate<String, String> bp1 = String::equals;
}
根据注意事项二,使用ClassName::method
二、构造器引用
与函数式接口相结合,自动与函数式接口中方法兼容。 可以把构造器引用赋值给定义的方法,与构造器参数 列表要与接口中抽象方法的参数列表一致!
格式 ClassName::new
实例1:
@Test
public void test5() {
Supplier<Employee> sup = () -> new Employee();
//构造器引用方式
Supplier<Employee> sup1 = Employee::new;//自动匹配无参构造
Employee employee = sup1.get();
System.out.println(employee);
}
因为Supplier接口中的抽象方法T get(); 是无参的,所以new 对象自动匹配无参构造
运行结果:
Employee{name='null', age=null, salary=0.0}
实例2:
@Test
public void test6() {
Function<Integer, Employee> fun = (x) -> new Employee(x);
Function<Integer, Employee> fun1 = Employee::new;//自动匹配有参构造
Employee emp = fun1.apply(100);
System.out.println(emp);
}
因为Function接口中的抽象方法R apply(T t); 有一个参数,所以new 对象自动匹配有一个参数的构造函数
运行结果:
Employee{name='null', age=100, salary=0.0}
三、数组引用
这里单独把数组引用拿出来实际上是强调一下,数组引用和构造引用基本相同,直接上一个实例来说明问题
格式 type[]::new
实例1:创建一个数组
@Test
public void test7() {
Function<Integer, String[]> fun = (x) -> new String[x];
String[] strs = fun.apply(10);
System.out.println(strs.length);
Function<Integer, String[]> fun1 = String[]::new;
String[] strs1 = fun.apply(20);
System.out.println(strs1.length);
}