Lambda表达式
Lambda表达式出现主要是为了简化代码,若某一个接口只有一个抽象方法,就能使用Lambda表达式来进行简化这个接口的实现类。
Lambda表达式的六种情况
JAVA
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | // 1 无参,无返回值 Runnable r = () -> System.out.println("1"); // 2 一个参数,无返回值 Consumer<String> con = (String s) -> { System.out.println(s); }; // 3 数据类型可以省略,编译器有类型推断 Consumer<String> con1 = (s) -> { System.out.println(s); }; // 4 若只需要一个参数,小括号能省略 Consumer<String> con2 = s -> { System.out.println(s); }; // 5 需要两个或以上的参数,可以有返回值,不只有一条语句 Comparator<Integer> com1 = (o1, o2) -> { System.out.println(o1); System.out.println(o2); return o1.compareTo(o2); }; // 6 Lambda体只有一条语句,大括号能省略,return也可以省略 Consumer<String> con3 = s -> System.out.println(s); |
Java内置的四大核心函数式接口
-
Consumer<T>
消费型接口 对T进行操作,不返回结果,方法为
void accept(T t)
-
Supplier<T>
供给型接口 不接收参数,返回类型T的数据,方法为
T get()
-
Function<T,R>
函数型接口 对类型为T的对象操作,返回R类型的数据,方法为
R apply(T t)
-
Predicate<T>
断定型接口 对类型T的数据进行判断,返回Boolean值,方法为
boolean test(T t)
方法引用
在lambda体中引用另一个方法,即用另一个方法来实现lambda体。
使用格式 类(或对象):: 方法名
- 对象::非静态方法
- 类::静态方法
- 类::非静态方法
方法引用的方法的形参列表和返回类型要与lambda一样才能使用该方法引用(针对于前两种格式)
主要是第三种格式有些难懂。
JAVA
1 2 3 4 5 | // 比如 Comparator 中的int compare(T1 t1, T2 t2) // String中的int t1.compareTo(t2) // 这种就是形参列表不一样,但是是由t1来调用一个t2参数的方法,所以就可以用第三种格式 // t1作为方法的调用者,t2作为形参 String::compareTo |
构造器引用
相当于lambda引用中创建一个对象,调用了一个构造方法。
JAVA
1 2 3 4 | // lambda表达式写法 Supplier<String> str = s -> new String(s); // 构造器引用的写法 Supplier<String> str = String::new; |
Stream流
Stream流的使用主要分为三个步骤。
- 创建Stream流。从数据源(集合,数组等)转换成Stream流。
- 中间操作。对数据源的数据进行处理。
- 终止操作。执行终止操作,就会执行中间操作的处理,产生结果。
创建Stream流
- 集合获取Stream流的方法
list.stream()
串行list.paralleStream()
并行
- 数组获取Stream流的方法
- 通过Arrays的静态方法stream()得到Stream流
Arrays.stream(int[])
- 通过Arrays的静态方法stream()得到Stream流
- 通过
Stream.of()
来获取Stream流 - 创建无限流(用于编造数据)
Stream.iterate()
Stream.generate()
Stream流的中间操作
-
筛选与切片
-
filter(Predicate p)
从流中排除某些元素,即满足Predicate函数的元素
-
limit(n)
截断流,使其元素不超过给定的元素,即筛选出来的元素不超过n
-
skip(n)
跳过元素,返回一个除了前n个数据的流,若数据源不足n个,则返回空流
-
distinct()
通过流生成元素的hashCode和equals方法去除重复的元素
-
-
映射
-
map(Function f)
接收一个函数作为参数,将元素转换成其他形式或提取信息
-
flatMap(Function f)
将一个函数作为参数,将流中的每个值都换成另一个流,然后把所有流连接成一个流
-
-
排序
-
sorted()
没有参数,自然排序,默认从小到大的排序,如果操作的元素是类,就会抛出异常,需要该类实现Comparable接口
-
sorted(Comparator com)
一个Comparator实例,定制排序
-
Stream流的终止操作
-
匹配与查找
-
boolean allMatch(Predicate p)
检查是否所有元素是否匹配该断定函数接口
-
boolean anyMatch(Predicate p)
检查是否至少有一个元素匹配该断定函数接口
-
boolean noneMatch(Predicate p)
检查是否没有元素匹配该断定函数接口
-
findFirst()
返回第一个元素
-
findAny()
返回任意一个元素
-
count()
返回流中的总个数
-
max(Comparator c)
返回流中的最大值
-
min(Comparator c)
返回流中的最小值
-
forEach(Consumer c)
内部迭代
-
-
归约
-
reduce(T identity, BinaryOperator<T> bin)
可以将流中元素反复结合起来得到一个值,返回这个T类型的值
比如这个求和的例子
list.stream.reduce(0, Integer::sum);
-
reduce(BinaryOperator<T> bin)
可以将流中元素反复结合起来得到一个值,返回这个
Optional<T>
类型的值
-
-
收集
collect(Collector c)
将流转换为其他形式的数据源,调用这个Collector接口的方法得到新建数据源
一般使用实现了接口的Collectors的类的方法
常用方法为
-
List<T> toList()
将元素收集到创建的List
-
Set<t> toSet()
将元素收集到创建的Set
-
Collection<T> toCollection()
将元素收集到创建的Collection
-
Long counting()
计算流中的个数
-
Integer summingInt()
对流中元素的整数属性求和
-
Double averagingInt()
求流中的元素Integer属性的平均值
Optional容器类
Optional<T>
类是一个容器类,可以报错类型T的值,代表这个值存在。
或者仅仅保存null,表示这个值不存在,可以避免空指针异常
如果值存在,则isPresent()方法返回true,调用get()方法会返回该对象
创建Optional类对象的方法
-
Optional.of(T t)
创建一个实例,t是非空的
-
Optional.isEmpty()
创建一个空的实例
-
Optional.ofNullable(T t)
创建一个实例,t是可以空的
判断Optional中是否包含对象
-
boolean isPresent()
判断是否包含对象
-
void ifPresent(Consumer<? super T> consumer)
如果有值就会执行Consumer接口的实现代码,并且会作为参数传给它
获取Optional容器的对象
-
T get()
如果调用对象包含值,则返回该值,否则抛异常
-
T orElse(T other)
如果有值则返回,没有返回指定的other值
-
T orElseGet(Supplier<? extends T> other)
如果有值就将其返回,否则返回由Supplier接口实现提供的对象
-
T orElseThrow(Supplier<? extends X> exceptionSupplier)
如果有值就将其返回,否则抛出由Supplier接口实现提供的异常