聚合操作
1.简介
Stream流是JDK 8但中新增加地接口,该接口可以将集合、数组中的元素转换为Stream流的形式,并结合Lambda表达式的优势进一步简化集合、数组中元素的查找、过滤、转换等操作。
2.实现步骤
- .将原始集合或数组对象转换为Stream流对象;
- 对Stream流对象中的元素进行一系列的过滤、查找等中间操作(Intermediate Operations),然后仍返回一个Stream流对象;
- 对Stream流进行遍历、统计、收集等终结操作(Terminal Operation),获取想要的结果。
//实例代码:
public class Demo1{
public static void main(String[] args){
//1.创建一个List集合对象
List<String> list = new ArrayList<>();
list.add("Java");
list.add("Python");
list.add("JavaScript");
list.add("C");
//2.创建一个Stream流对象
Stream<String> stream = list.stream();
//3.对Stream流中的元素分别进行过滤、截取操作
Stream<String> stream2 = stream.filter(i -> i.startsWith("张"));
Stream<String> stream3 = stream2.limit(2);
//4-1.对Stream中的元素进行终结操作,进行遍历输出
stream3.forEach(j-> System.out.println(j));
System.out.println("-----------");
//4-2.通过链式表达式的形式完成聚合操作
list.stream().filter(i->i.startsWith("张"))
.limit(2)
.forEach(j-> System.out.println(j));
}
}
输出:
张三
张小明
-----------
张三
张小明
特别注意:在进行聚合操作时,只是改变了Stream流对象中的数据,原来的数据并不会被改变。
3.Stream流对象的创建
3种Stream流的创建方式
- 所有的Collection集合都可以使用stream()静态方法获取Stream流对象;
- Stream接口的of()静态方法可以获取基本类型包装类数据、引用数据类型数据和单个元素的Stream流对象;
- Arrays数组工具类的stream()静态方法也可以获取数组元素的Stream流对象。
//实例
public class Demo02{
public static void main(String[] args){
//创建一个数组
Integer[] array = {9,7,6,1,3};
//将数组转换为List集合
List<Integer> list = Arrays.asList(array);
//1.使用集合对象的stream()静态方法创建Stream()流对象
Stream<Integer> stream1 = list.stream();
stream.forEach(i-> System.out.print(i + " "));
System.out.println();
//2.使用Stream接口的of()静态方法创建Stream对象
Stream<Integer> stream2 = Stream.of(array);
stream2.forEach(i-> System.out.print(i + " "));
System.out.println();
//3.使用Arrays数组工具类的stream()静态方法创建Stream流对象
Stream<Integer> stream3 = Arrays.stream(array);
stream3.forEach(i-> System.out.print(i + " "));
}
}
输出:
9 7 6 1 3
9 7 6 1 3
9 7 6 1 3
4.常用方法
-
forEach() 遍历
输出Stream流对象中的元素。
public class Demo03{ public static void main(String[] args){ //通过字符串源数据创建一个Stream流对象 Stream<String> stream = Stream.of("张三", "李四", "张小明", "张阳"); //使用forEach()遍历Stream流对象中的元素 stream.forEach(i-> System.out.print(i + " ")); } }
输出:
张三 李四 张小明 张阳
-
filter() 过滤
将一个Stream流中的元素进行筛选转化为一个新的子集流。
public class Demo04{ public static void main(String[] args){ Stream<String> stream = Stream.of("张三", "李四", "张小明", "张阳"); stream.filter(i->i.startsWith("张")) //筛选以“张”开头的元素 .filter(i->i.length()>2) //筛选长度大于2个的元素 .forEach(System.out::println); //对流元素进行遍历输出 // 使用逻辑运算符 //stream.filter(i->i.startsWith("张")&&i.length()>2).forEach(System.out::println); } }
输出:
张小明
-
map() 映射
该方法将流对象中的元素通过特定的规则进行修改然后映射至另一个流对象中。
public class Demo05{ public static void main(String[] args){ Stream<String> stream = Stream.of("a1", "a2", "b1", "c1", "c2"); stream.filter(s->s.startsWith("c")) .map(String::toUpperCase) //对流元素进行映射,将全部字符改为大写 .sorted() //对流元素进行排序 .forEach(System.out::println); } }
输出:
C1 C2
-
limit() 截取
该方法用于输出流对象中的前n个元素,大多情况下,limit()一般与skip()方法(跳过指定数目元素)组合使用,用于截取流对象中指定位置的多个元素。
public class Demo06{ public static void main(String[] args){ //使用limit截取流对象中的元素 Stream<String> stream6 = Stream.of("张三", "李四", "张小明", "张阳"); stream6.skip(1) //跳过流中地前一个元素 .limit(2) //截取流中的前两个元素 .forEach(System.out::println); } }
输出:
李四 张小明
-
collect() 收集
collect(收集)是一种有效的终结操作,可以将Stream流中的元素保存为另一种形式,如集合、字符串。
collect()方法使用Collector作为参数,Collector包含四种不同的操作:
supplier(初始构造器)、accumulator(累加器)、combiner(组合器)、finisher(终结者);
在JDK 8中这些方法已经内置在了java.util.stream包下的Collectors类中
public class Demo07{ //使用collect()将Stream流中的元素保存为另一种形式,如集合、字符串 public static void main(String[] args){ Stream<String> stream1 = Stream.of("张三", "李四", "张小明", "张阳"); //使用filter()方法筛选出字符串以“张”开头的元素 //再使用collect()方法进行终结操作,将流元素收集到一个List集合中 List<String> list = stream1.filter(i -> i.startsWith("张")) .collect(Collectors.toList()); System.out.println(list); System.out.println("-----------------"); Stream<String> stream2 = Stream.of("张三", "李四", "张小明", "张阳"); //使用filter()方法筛选出字符串以“张”开头的元素 //再使用collect()方法进行终结操作,将流元素使用“and”连接到收集到一个字符串中 String string = stream2.filter(i -> i.startsWith("张")) .collect(Collectors.joining("and")); System.out.println(string); } }
输出:
[张三, 张小明, 张阳] ----------------- 张三and张小明and张阳