文章目录
1.Lambda表达式的基础语法
Lambda是一个匿名函数,可以把Lambda表达式理解为是一段可以传递的代码(将代码像数据一样进行传递)。可以写出更简洁、更灵活的代码。作为一种更紧凑的代码风格,使Java的语言表达能力得到了提升。
**简单来说就是将原来的匿名内部类的写法进行简化。
**
1.1 语法一 无参数,无返回值
这里我们找到一个接口叫做runnable
你看,就是这么个接口,就一个方法run,没有参数也没有返回值。最重要的是他加了一个@FunctionalInterface的注释(才可以lambda),完全符合我们的要求。
下面我们给出代码
如果只有一条语句可以不用大括号
Runnable r = new Runnable() {
@Override
public void run() {
// TODO Auto-generated method stub
System.out.println("匿名类原来的写法");
}
};
r.run();
}
Runnable r = ()->System.out.println("你没见过的全新lambda形式");
r.run();
这么一改我们可以发现,使用lambda表达式可以减少很多代码量,很方便。而且!!给人感觉你很厉害!!
1.2 语法二 一个参数,无返回值
这一次我们也是先找系统中已有的一个参数无返回值的函数式接口。没错,就是 Consumer接口,有兴趣的同学可以自己shift+ctrl+t查找,查看其源码。
如果一个参数,那么可以不写小括号
Consumer<String> c1 = (x)->System.out.println(x);
Consumer<String> c2 = x->System.out.println(x);
c1.accept("一个参数,无返回值");
c2.accept("一个参数可以不加括号哦!");
1.3语法三 有两个以上的参数,有返回值还有多条语句。
本次我们实现Comparator类以及自己再定义个函数式接口getSum。
实现Comparator接口的比较方法,若第一个参数大于第二个参数则返回正数,否则返回负数
Comparator<Integer> ci = (x1,x2)->{
Integer i = x1.compareTo(x2);
return i;
};
System.out.println(ci.compare(1, 2));
实现自己定义的接口GetSum,注意两点,接口中只有一个抽象方法,而且需要加注释@FunctionalInterface。
只有一个return语句的时候可以省略大括号和return关键字
@FunctionalInterface
interface GetSum<T>{
T run(T t1,T t2);
}
`public static void main(String[] args) {
GetSum<Integer>g1 = (x1,x2)->x1+x2;
System.out.println(g1.run(10, 20));
}
2.四大核心内置函数式接口
虽然函数式接口,我们可以自己定义编写,但是有些常用的系统已经为我们写好了 ,可以很方便地拿来使用。
还有一定,在Stream流的方法中,有许多方法的参数就是内置函数式接口。
这四大核心内置函数式接口,接下来为大家介绍一下。代码与上面的差不多,就简单介绍一下功能。
2.1 Consumer :消费型接口
其中的方法是void accept(T t);
Consumer接口,从其唯一的accept方法中我们可以看出,这个接口他是属于一个参数无返回值的接口。所以叫消费型接口。
2.2 Supplier :供给型接口
其中的方法是T get();
Supplier接口,发现其get方法没有参数,却有泛型返回值,所以叫攻击性接口。
2.3 Function< T , R > :函数型接口
其中的方法是R apply(T t);
一个参数一个返回值,就像函数一样。
2.4 Predicate :断言型接口
其中的方法是boolean test(T t);
一个参数,返回值固定为boolean类型,所以是拿来做判断的。
2.5 其他接口
3.方法引用、构造器引用与数组引用
3.1方法引用
除了我们直接写lambda表达式外,函数式接口还可以直接调用已经实现的方法,但是返回值和参数要相符合
有三种语法格式:
- 对象::实例方法名
- 类::静态方法名
- 类::实例方法名
package textLambda;
import java.io.PrintStream;
import java.util.Comparator;
import java.util.function.BiPredicate;
import java.util.function.Consumer;
import org.junit.Test;
public class Testtest {
@Test
public void test1(){
//对象::实例方法名
PrintStream ps = System.out;
Consumer c1 = ps::println;
c1.accept("ps是PrintStream的一个对象,我们可以用对象::实例方法名");
}
@Test
public void test2(){
//类::静态方法名
//实现比较功能,若第一个小于第二个返回-1
Comparator<Integer> c1 = Integer::compareTo;
System.out.println(c1.compare(-5, 2));
}
@Test
public void test3(){
//类::实例方法名
//实现比较功能,
BiPredicate<String,String> bp=(x,y)->x.equals(y);
BiPredicate<String, String> bp2=String::equals;
System.out.println(bp2.test("123", "123"));
}
}
3.2 构造器引用
注意:需要调用的构造器的参数列表要与函数式接口中抽象方法的参数列表保持一致!
public static void main(String[] args) {
//使用无参构造方法
Supplier<Employee> se = Employee::new;
Employee e1 = se.get();
//使用一个参数构造方法
Function<Integer, Employee> fie = Employee::new;
Employee e2 = fie.apply(12);
System.out.println(e2.getAge());
}
3.3 数组引用
public static void main(String[] args) {
Function<Integer, String[]> fis = (x)->new String[10];
String[] arrStr = fis.apply(10);
System.out.println(arrStr.length);
}