Java8新特性:Stream流
1、Stream源操作
public static void main(String[] args) {
//1、将集合中的数据转换成流
List<String> strings = Arrays.asList("jams", "jerry", "tom","jdk8","acd");
List<String> j = strings.stream() //将集合中的数据转换成流
.filter(s -> s.startsWith("j")) //过滤出流中以“j"开头的数据
.map(String::toUpperCase) //将流中过滤出的数据转换成大写
.sorted() //将数据排序
.collect(Collectors.toList()); //将流转换成集合
System.out.println(j);
//2、将数组数据转换成流
String[] players = {"james","kebe"};
Stream<String> j1 = Stream.of(players).filter(s -> s.contains("j")).map(String::toLowerCase);
System.out.println(j1);
}
2、stream的中间操作–无状态操作
2.1、Stream的filter函数与谓词逻辑
实体类
private Integer id;
private Integer age;
private String gender;
private String firstName;
private String lastName;
public static Predicate<Employee> ageThan70 = x -> x.getAge()>70;
public static Predicate<Employee> genderM = x -> x.getGender().equals("M");
//新建对象
Employee e1 = new Employee(1,23,"M","Rick","Between");
Employee e2 = new Employee(2,24,"P","Tom","lowan");
Employee e3 = new Employee(3,25,"M","Helln","Maria");
//将对象封装
List<Employee> employees = Arrays.asList(e1, e2, e3);
List<Employee> m = employees.stream()
// .filter(e -> e.getAge() < 70 && e.getAge() > 24 && e.getGender().equals("M"))
.filter(Employee.ageThan70.and(Employee.genderM).negate())//negate()取反的意思
.collect(Collectors.toList());
System.out.println(m);
2.2、使用peek替换map的return语句
public static void main(String[] args) {
//新建对象
Employee e1 = new Employee(1,23,"M","Rick","Between");
Employee e2 = new Employee(2,24,"P","Tom","lowan");
Employee e3 = new Employee(3,25,"M","Helln","Maria");
List<Employee> employees = Arrays.asList(e1, e2, e3);
List<Employee> male = employees.stream()
.map(x -> {
x.setAge(x.getAge() + 1);//将所有年龄加1
x.setGender(x.getGender().equals("male") ? "P" : "Female");//所有人性别对调
return x;
}).collect(Collectors.toList());
//或者使用以下方法
// List<Employee> male2 = employees.stream()
// .peek(x -> {
// x.setAge(x.getAge() + 1);//将所有年龄加1
// x.setGender(x.getGender().equals("male") ? "P" : "Female");//所有人性别对调
// }).collect(Collectors.toList());
System.out.println(male);
}
2.3、Map与flatMap区别
public static void main(String[] args) {
List<String> strings = Arrays.asList("hello", "word");
strings.stream()
.map(w->w.split("")) //[h,e,l,l,o],[w,o,r,l,d]
.collect(Collectors.toList());
System.out.println("====================");
strings.stream()
.flatMap(w -> Arrays.stream(w.split("")))
.forEach(System.out::println);//输出为h,e,l,l,o,w,o,r,l,d
}
2.4、做数据格式的转换
List<String> aplha = Arrays.asList("Monkey", "Lion", "Giraffe", "Lemur");
//1、不使用管道流
List<String> alphaUpper = new ArrayList<>();
for(String s :aplha){
alphaUpper.add(s.toUpperCase());
}
System.out.println(alphaUpper);
//2、使用管道流
alphaUpper = aplha.stream().map(String::toLowerCase).collect(Collectors.toList());
2.5、做数据类型的转换
List<String> aplha = Arrays.asList("Monkey", "Lion", "Giraffe", "Lemur");
//2、做数据类型的转换
Stream.of("Monkey","Lion","Giraffe")
.mapToInt(String::length) //判断字符串长度,并转换成int
.forEach(System.out::println); //遍历循环输出
3、stream的中间操作–有状态操作
limit():取前几个
skip():跳过前几个
distinct():去重
sorted():排序
4、像sql一样排序集合
Comparator接口
5、函数式接口
5.1、default关键字
接口:
测试:
5.2、自定义方法实现Comparator接口的方法
6、Steam查找与匹配元素
6.1、anyMach():匹配集合中是否有符合特定条件的元素
import java.util.Arrays;
import java.util.List;
/**
* @Description :
* @Author :
* @Date :2021/4/14 10:39
*/
public class StreamTest09 {
public static void main(String[] args) {
//新建对象
Employee e1 = new Employee(1,23,"M","Rick","Between");
Employee e2 = new Employee(2,24,"P","Tom","lowan");
Employee e3 = new Employee(3,71,"M","Helln","Maria");
List<Employee> employees = Arrays.asList(e1, e2, e3);
//使用for循环判断集合种是否有年龄大于70的元素
boolean isExistAgeThan70 = false;
for(Employee employee:employees){
if(employee.getAge()>70){
isExistAgeThan70 = true;
break;
}
}
System.out.println(isExistAgeThan70);
//1、使用anyMatch匹配集合中是否有年龄大于70的元素
isExistAgeThan70 = employees.stream().anyMatch(e -> e.getAge() > 70);
System.out.println(isExistAgeThan70);
//使用谓词匹配集合中是否有年龄大于70的元素
isExistAgeThan70 = employees.stream().anyMatch(Employee.ageThan70);
System.out.println(isExistAgeThan70);
}
}
6.2、allMatch()判断集合中的元所有素是否符合条件
public class StreamTest09 {
public static void main(String[] args) {
//新建对象
Employee e1 = new Employee(1,23,"M","Rick","Between");
Employee e2 = new Employee(2,24,"P","Tom","lowan");
Employee e3 = new Employee(3,71,"M","Helln","Maria");
List<Employee> employees = Arrays.asList(e1, e2, e3);
//2、使用allMatch()判断集合中的元所有素是否符合条件
Boolean isExistAgeThan10 = employees.stream().allMatch(e->e.getAge()>10);
System.out.println("isExistAgeThan10:"+isExistAgeThan10);
}
}
控制台输出:
6.3、noneMatch()判断集合中是否不存在所有素是否符合条件
public class StreamTest09 {
public static void main(String[] args) {
//新建对象
Employee e1 = new Employee(1,23,"M","Rick","Between");
Employee e2 = new Employee(2,24,"P","Tom","lowan");
Employee e3 = new Employee(3,71,"M","Helln","Maria");
List<Employee> employees = Arrays.asList(e1, e2, e3);
//3、使用noneMatch()判断集合中是否不存在所有素是否符合条件
Boolean isExistAgelower10 = employees.stream().noneMatch(e->e.getAge()<10);
System.out.println("集合中不存在年龄小于10的元素:"+isExistAgelower10);
}
}
控制台输出:
6.4、findFirst():查找集合中符合条件的第一个元素。
//4、findFirst()查找集合中符合条件的第一个元素。
//Optional判断该值是否存在,如果存在使用get()取出
Optional<Employee> optional
= employees.stream()
.filter(e -> e.getAge() > 23)
.findFirst();
System.out.println(optional.get());//get()取出该元素
控制台输出:
6.5、isPresent():判断集合中符合条件的第一个元素是否存在,返回值Boolean
//5、isPresent():判断集合中符合条件的第一个元素是否存在,返回值Boolean
Boolean b = employees.stream()
.filter(e -> e.getAge() > 23)
.findFirst()
.isPresent();
System.out.println(b);
控制它输出:
6.6、ifPresent():判断集合中符合条件的第一个元素是否存在,如果存在进行打印
//6、ifPresent():判断集合中符合条件的第一个元素是否存在,如果存在进行打印
employees.stream()
.filter(e -> e.getAge() > 23)
.findFirst()
.ifPresent(e-> System.out.println(e));
控制台输出:
7、reduce():stream集合元素归约
7.1、用串行流规约
package com.cui.lambda;
import com.cui.lambda.beans.Employee;
import java.util.Arrays;
import java.util.List;
/**
* @Description :
* @Author :cui
* @Date :2021/4/14 11:33
*/
public class GuiYue {
public static void main(String[] args) {
//1、整数类型数据的归约
List<Integer> list = Arrays.asList(1,2,3,4,5);
Integer resultSum = list.stream().reduce(0, Integer::sum);
System.out.println(resultSum);
//2、char字符的归约
List<String> listStr = Arrays.asList("h","e","l","l","0");
String resultString = listStr.stream().reduce("", String::concat);
System.out.println(resultString);
//3、对象数据归约
Employee e1 = new Employee(1,23,"M","Rick","Between");
Employee e2 = new Employee(2,24,"P","Tom","lowan");
Employee e3 = new Employee(3,25,"M","Helln","Maria");
List<Employee> employeeLIst = Arrays.asList(e1,e2,e3);
Integer ageSum = employeeLIst.stream().map(e -> e.getAge()).reduce(0, Integer::sum);
System.out.println(ageSum);
}
}
控制台输出:
7.2、parallelStream():并行流规约
原理:
案例:
reduce()有三个参数:
第一个初始值;
第二个累加器;
第三个合并器;
//对象数据归约
Employee e1 = new Employee(1,23,"M","Rick","Between");
Employee e2 = new Employee(2,24,"P","Tom","lowan");
Employee e3 = new Employee(3,25,"M","Helln","Maria");
List<Employee> employeeLIst = Arrays.asList(e1,e2,e3);
//用并行流计算
Integer ageSum2 = employeeLIst.parallelStream()
.map(e -> e.getAge())
.reduce(0, Integer::sum,Integer::sum);
System.out.println(ageSum2);
控制台输出: