Java 8
一、Lambda表达式
一种简洁的表示,可传递的匿名函数的一种方式:没有名称、没有参数、没有函数主体
基础语法
java 8中引入了新的操作符"->",该操作符可以称为箭头操作符,或者lambda操作符,将lambda分成两部分。
- 箭头左侧:lambda表达式的参数列表
- 箭头右侧:lambda表达式中需要执行的功能,即lambda主体
语法:
-
无参数,无返回值
()-> System.out.println("Hello");
-
有参数、无返回值
(i) -> System.out.println(i*2); or i -> System.out.println(i*2);
-
多参数、有返回值
(x,y) -> x + y;
在lambda中的参数列表,可以不用写参数类型,自动根据上下文做类型的推断。
Lambda 需要有接口的支持
函数式接口定义:接口中只有一个抽象方法的接口,成为函数式接口;
使用@FunctionalInterface注解修饰,对该接口做检查;
如果接口里,有多个抽象方法,使用该注解,会有语法错误
二、方法的引用
**语法:**指向静态方法、实例方法、对象实例方法、构造器的引用,
1.指向静态方法的方法引用,例如Integer的parseInt方法 ,可以写成Integer::parseInt;
//类::静态方法名
Integer::parseInt;
2.指向任意类型实例方法的方法引用,例如String的length方法,写成String::length;
//类::实例方法名
String::length;
3.指向现有对象的实例方法的方法引用
//对象::实例方法名
三、构造函数的引用
构造器的引用:对于一个现有构造函数,你可以利用它的名称和关键字new来创建它的一个引用ClassName::new;
// 类名::new
ClassName::new;
四、Stream接口简介
Java 8 是一个非常成功的版本,这个版本新增的Stream,配合 同版本出现的 Lambda,给我们操作集合(Collection)。提供了极大的便利
什么是Stream呢?
Stream 将要处理的元素看做一种流,在流的过程中,借住Stream API对流中的元素进行操作,比如:筛选,排序,聚合等。
Stream 可以由数组或集合创建,对流的操作分为两种:
- 中间操作:没测返回一个新的流,可以有多个。
- 终端操作,每个流只能进行一次终端操作,终端操作会产生一个新的集合或值。
另外: Stream 有几个特性:
- stream不存储数据,而是按照特定的规则对数据进行计算,一般会输出结果。
- stream不会改变数据源。通常情况下一个新的集合或一个值。
- stream具有延迟性特性,只能调用中终端操作时,中间操作才会执行。
Stream的使用
数组
Stream可以通过集合或者数组创建。
Stream包括的静态方法有:
of()、iterate()、generate()
// of 为添加数,用流的方式返回
Stream<Integer> stream = Stream.of(1, 2, 3, 4, 5, 6);
// iterate(第一个参数为起始值,第二个参数是增量值).limit(是截取的长度),最终返回一个流
Stream<Integer> stream2 = Stream.iterate(0, (x) -> x + 3).limit(4);
stream2.forEach(System.out::println);
// 返回无序流,一般参数是创建随机数。
Stream<Double> stream3 = Stream.generate(Math::random).limit(3);
stream3.forEach(System.out::println);
集合
-
过滤(
filter
)// 过滤list中比4大的数据直接打印 list.stream().filter(x -> x > 4).forEach(System.out::println);
- 匹配第一个值
filter.findFirst()
Optional<Integer> findFirst = list.stream().filter(x -> x > 6).findFirst();
- 匹配任意(适用于并行流)
Optional<Integer> findAny = list.parallelStream().filter(x -> x > 6).findAny();
- 匹配第一个值
-
聚合(
max/min/count
)-
获取最大值(
max
)// 自然排序顺序 Optional<Integer> max = list.stream().max(Integer::compareTo); // 自定义排序 Optional<Integer> max2 = list.stream().max(new Comparator<Integer>() { @Override public int compare(Integer o1, Integer o2) { return o1.compareTo(o2); } }); // 查询工资最高的人 Optional<Person> max = personList.stream().max(Comparator.comparingInt(Person::getSalary));
-
获取数量(
count
)list.stream.filter(x -> x > 6).count();
-
-
映射(
map/flatMap
)- 可以将一个流的元素按照一定的映射规则映射到另一个流中。分为
map
和flatMap
map
:接收一个函数作为参数,该函数会被应用到每一个元素中,并将其映射成一个新的元素。flatMap
:接受一个函数作为参数,将流中的每个值都换成另一个流,然后把所有的流连接成一个流。
- 可以将一个流的元素按照一定的映射规则映射到另一个流中。分为
-
收集(
collect
)将最终的指收集成一个指也可以收集成一个新的集合。
-
归集(
toList/toSet/toMap
)collect(collects.toList)
因为流不存储数据,那么在流中的数据完成处理后,需要将流中的数据重新归集到新的集合中。
toList
、toSet
和toMap
比较常用,另外还有toCollection
、toConcurrentMap
等复杂一些的用法。 -
统计(
count/averaging
)Collectors提供了一系列用于数据统计的静态方法:
- 计数:
count
- 平均值:
averagingInt、averagingLong、averagingDouble
- 最值:
maxBy、minBy
- 求和:
summingInt、summingLong、summingDouble
- 统计以上所有:
summarizingInt、summarizingLong、summarizingDouble
// 求总数 Long count = personList.stream().collect(Collectors.counting()); // 求平均工资 Double average = personList.stream().collect(Collectors.averagingDouble(Person::getSalary)); // 求最高工资 Optional<Integer> max = personList.stream().map(Person::getSalary).collect(Collectors.maxBy(Integer::compare)); // 求工资之和 Integer sum = personList.stream().collect(Collectors.summingInt(Person::getSalary)); // 一次性统计所有信息 DoubleSummaryStatistics collect = personList.stream().collect(Collectors.summarizingDouble(Person::getSalary));
- 计数:
-
分组(
partitioningBy/groupingBy
)personList.stream().collect(Collectors.partitioningBy(x -> x.getSalary() > 8000));
-
接合(joining)
在每个对象后添加字符
list.stream().collect(Collectors.joining("-"));
-