title: 初识STREAM
date: 2020-11-26 13:18:38
tags: java

概述

Stream流一般分为三个步骤:

  1. 创建stream流,可以从集合或数组中获取流
  2. 流的中间操作,可以对流进行筛选,跳过等数据操作
  3. 流的终止,可以将其收集为数组或获取到某种数据

接下来从以上三个方面阐述stream的编码过程。


创建stream流

可以从数组中获取流,或根据数组创建流,常见的创建方式有:

  1. //从list获取
  2. Stream <String> s1 = Arrays.asList("a","b","c").stream();
  3. //直接创建
  4. Stream <String> s2 = Arrays.stream("a","b","c");
  5. Stream <String> s3 = Stream.of("a","b","c");

流的中间操作

流的中间操作会返回一个操作结果后的流,同时其形式像这样:

  1. stream = stream.operator();

常见的流中间操作有:

filter当返回值为true时保留该流对象,为false则过滤该对象。例如筛选年龄大于20岁的学生:
  1. Stream <Student> stream = stream.filter((e)->{
  2. return e.getAge()>=20;
  3. } ); //e的数据类型为<XXX>定义的数据类型,这里e是Student类的

skip(n),跳过前n个元素
  1. stream = stream.skip(1); //跳过第一个元素

distinct(),根据equals()和hashcode()进行去重
  1. stream = stream.distinct(); //去除重复元素

sorted(Comparator),根据选择器排序
  1. stream = stream.sorted(); //自然语序排序
  2. stream = stream.sorted((o1,o2)->{
  3. return o1.getAge() - o2.getAge();
  4. }) //使用lambda语句进行排序
  5. stream = stream.sorted(new Comparator<Student>(){
  6. @Override
  7. public int compare(Student s1,Student s2){
  8. return s1.getAge() - s2.getAge();
  9. }
  10. }); //使用自定义的Comparator进行排序

map(),flatMap()均是将每一个流对象进行操作,map返回流本身,flatMap返回操作结果的流额外进行了flat的合并处理,为此要求了flatMap的函数返回值必须是List或stream,不然无法进行flat处理。
  1. //定义一个小写转大写的函数
  2. public static Stream <Charactor> upper(String str){};
  3. Stream <String> streams = Stream.of("a","bbb","cc"); //将三个字符串看成三个流对象
  4. Stream <Stream <Charactor> >streams2 = streams.map(e->upper(e)); //对每个流对象处理得到一个流,所以运行结果是一个含三个流的流对象
  5. Stream <Charactor> stream3 = streams.flatMap(MAIN::upper); //这里同样得到三个流后对流进行了合并flat操作,所以结果是一个只含有字符的流对象

终止操作

终止操作分为两种,查询和收集。查询指最终结果是某一种数据形式,如查询所有人年龄的最大值,查询名字中含“a”的人的姓名。收集指结果是数组形式,是包含多个数据对象的结果。

查询操作

查询操作有allMatch,anyMatch,findFirst,max,min等操作类型,例如:

  1. boolean result1 = stream.allMatch(e->e.getName().length()>=2); //判断所有人的姓名长度是否都大于2
  2. boolean result2 = stream.anyMatch(e->e.getAge() >=30); //判断是否有人年龄大于30
  3. Optional <Student> first = stream.findFirst(); //使用Optional接住查询结果
  4. Systeam.out.println(first.get()); //使用get()方法取得在Optional里的Student对象
  5. Optional <Integer> maxAge = stream.max((o1,o2)->{ //max里面使用lambda写好Comparator
  6. return o1.getAge() - o2.getAge();
  7. }); // 同样使用Optional接住查询结果
  8. System.out.println(maxAge.get()); //打印get到的Integer对象

收集操作

收集操作一般使用一个Collertor存储stream流的处理结果,如list/set/map,也可以使用.collect(Collectors.XXX())的方法来取得想要的结果。

  1. List <String> list = stream.map(e-> e.getName()).collect(Collectors.toList()); //使用toList将stream存储到list中
  2. Map <String,Integer> map = stream.collect(Collectors.toMap(e->e.getName(),e2->e2.getAge())); //使用toMap将stream存储到map中
  3. Optional <Student> max2 = stream.collect(Collectors.maxBy((a1,a2)-> a1.getAge()-a2.getAge())); //使用get就可以获取到年龄最大的Student对象