Jdk8新特性
作者:互联网
1. 函数式接口
定义:接口中只有一个抽象方法的接口称为函数式接口,在接口上使用@FunctionalInterface标记
类型 | 接口名 | 抽象方法 |
---|---|---|
消费型接口 | Consumer |
void accept(T t) |
供给型接口 |
Supplier |
T get() |
判断型接口 | Predicate |
boolean test(T t) |
功能型接口 | Function<T,R> | R apply(T t) |
2. lambda表达式
定义:只有函数式接口才能使用lambda表达式,本质上lambda表达式是用于实现函数式接口的抽象方法
语法:(形参列表)-> {方法体/lambda体}
当形参列表中只有一个参数时()可以省略
当lambda体中只有一条语句时{}可以省略;当该条语句是return语句时,return也可省略
3. 方法引用与构造器引用
方法引用和构造器引用都是为了简化lambda表达式
3.1 方法引用语法和适用条件
语法: 类名::静态方法名/实例方法名
对象名::实例方法名
适用条件:
-
lambda体只有一条语句,并且是通过调用一个对象或类的现有方法来完成的
-
lambda表达式的形参正好是给该方法的实参,或调用第一个参数的成员方法并把剩余的参数按照顺序传入该成员方法中
t->System.out.println(t) => System.out::println () -> Math.random() => Math::random t->System.out.println("hello world") 不能使用方法引用 Arrays.sort(arr, (s1,s2) -> s1.compareToIgnoreCase(s2)) => Arrays.sort(arr, String::compareToIgnoreCase)
3.2 构造器引用
语法: 类名::new
数组类型名::new
适用条件:
-
当lambda表达式是用于创建一个对象,并满足lambda表达式的形参列表是给创建该对象的构造器的实参列表
-
当lambda表达式是用于创建一个数组对象,并满足lambda表达式的形参是给创建该数组对象的长度
Function<Integer,String[]> f = (Integer len) -> new String[len] => Function<Integer,String[]> f = String[]::new Stream<BigDecimal> stream2 = stream.map(num -> new BigDecimal(num)) => Stream<BigDecimal> stream2 = stream.map(BigDecimal::new)
4. Stream流
特点: stream不会自己存储元素;不会改变源对象,每次处理都会返回一个持有结果的新stream;stream操作是延迟执行的
**只有终止操作执行时中间操作链才会依次执行,并结束该stream**
操作步骤: 创建stream --> 中间操作链 --> 终止操作
4.1 创建stream
1、创建 Stream方式一:通过集合
Java8 中的 Collection 接口被扩展,提供了两个获取流的方法:
-
public default Stream
stream() : 返回一个顺序流 -
public default Stream
parallelStream() : 返回一个并行流 获取一个并行流: Stream.of(1, 2, 3).parallel() Arrays.asList(1,2,3).parallelStream()
Map获取stream流:
new HashMap<String, String>().entrySet().stream()
2、创建 Stream方式二:通过数组
Java8 中的 Arrays 的静态方法 stream() 可以获取数组流:
- public static
Stream stream(T[] array): 返回一个流
重载形式,能够处理对应基本类型的数组:
- public static IntStream stream(int[] array):返回一个整型数据流
- public static LongStream stream(long[] array):返回一个长整型数据流
- public static DoubleStream stream(double[] array):返回一个浮点型数据流
3、创建 Stream方式三:通过Stream的of()
可以调用Stream类静态方法 of(), 通过显示值创建一个流。它可以接收任意数量的参数。
- public static
Stream of(T... values) : 返回一个顺序流
4、创建 Stream方式四:创建无限流
可以使用静态方法 Stream.iterate() 和 Stream.generate(), 创建无限流。
- public static
Stream iterate(final T seed, final UnaryOperator f):返回一个无限流 - public static
Stream generate(Supplier s) :返回一个无限流
Stream<Integer> stream = Stream.iterate(1, num -> num+=2);
Stream<Double> stream = Stream.generate(Math::random);
5、Stream.concat(): 合并两个流并返回一个新的流
static <T> Stream<T> concat(Stream<? extends T> firstStream,
Stream<? extends T> secondStream)
- 此方法创建一个延迟连接的流,其元素是firstStream的所有元素,后跟secondStream的所有元素。
- 如果两个输入流都是有序的,则对所得到的流进行排序。
- 如果任一输入流是并行的,则得到的流是平行的。
- 关闭结果流时,将调用两个输入流的关闭处理程序。
4.2 中间操作
方 法 | 描 述 |
---|---|
filter(Predicate p) | 接收 Lambda , 从流中排除某些元素 |
distinct() | 筛选,通过流所生成元素的equals() 去除重复元素 |
limit(long maxSize) | 截断流,使其元素不超过给定数量 |
skip(long n) | 跳过元素,返回一个扔掉了前 n 个元素的流。若流中元素不足 n 个,则返回一个空流。与 limit(n) 互补 |
peek(Consumer action) | 接收Lambda,对流中的每个数据执行Lambda体操作 |
sorted() | 产生一个新流,其中按自然顺序排序 |
sorted(Comparator com) | 产生一个新流,其中按比较器顺序排序 |
map(Function f) | 接收一个函数作为参数,该函数会被应用到每个元素上,并将其映射成一个新的元素。 |
mapToDouble(ToDoubleFunction f) | 接收一个函数作为参数,该函数会被应用到每个元素上,产生一个新的 DoubleStream。 |
mapToInt(ToIntFunction f) | 接收一个函数作为参数,该函数会被应用到每个元素上,产生一个新的 IntStream。 |
mapToLong(ToLongFunction f) | 接收一个函数作为参数,该函数会被应用到每个元素上,产生一个新的 LongStream。 |
flatMap(Function f) | 接收一个函数作为参数,将流中的每个值都换成另一个流,然后把所有流连接成一个流 |
4.3 终止操作
方法 | 描述 |
---|---|
boolean allMatch(Predicate p) | 检查是否匹配所有元素 |
boolean anyMatch(Predicate p) | 检查是否至少匹配一个元素 |
boolean noneMatch(Predicate p) | 检查是否没有匹配所有元素 |
Optional |
返回第一个元素 |
Optional |
返回当前流中的任意元素 |
long count() | 返回流中元素总数 |
Optional |
返回流中最大值 |
Optional |
返回流中最小值 |
void forEach(Consumer c) | 迭代 |
T reduce(T iden, BinaryOperator b) | 可以将流中元素反复结合起来,得到一个值。返回 T |
U reduce(BinaryOperator b) | 可以将流中元素反复结合起来,得到一个值。返回 Optional |
R collect(Collector c) | 将流转换为其他形式。接收一个 Collector接口的实现,用于给Stream中元素做汇总的方法 使用Collector的Collectors工具类 |
Stream.of(1,2,4,5,7,8).reduce((t1,t2) -> t1>t2?t1:t2)
Stream.of(1,2,4,5,7,8).reduce(0, (t1,t2) -> t1+t2)
如果没有指定初始值,默认将第一个元素多为初始值 Stream.of(1,2).reduce((result, t) -> result + t)
boolean foundAny = false;
T result = null;
for (T element : this stream) {
if (!foundAny) {
foundAny = true;
result = element;
}
else
result = accumulator.apply(result, element);
}
return foundAny ? Optional.of(result) : Optional.empty();
Collectors的静态方法
5. Optional类
Optional实际上是个容器:它可以保存类型T的值,或者仅仅保存null
其他方法:
public Optional<T> filter(Predicate<? super T> predicate)
public<U> Optional<U> map(Function<? super T, ? extends U> mapper)
public<U> Optional<U> flatMap(Function<? super T, Optional<U>> mapper)
通常使用 Optional.ofNullable() 方法将一个对象封装成为一个Optional对象
如果要返回一个空对象,则可以使用Optional.empty()进行封装
获取容器中的对象是建议使用orElseGet
标签:Stream,stream,元素,特性,Jdk8,Optional,public,lambda 来源: https://www.cnblogs.com/-w-k-/p/16662572.html