【JavaSE】Java基础语法(三十二):Stream流

115 阅读5分钟

文章目录


\

在这里插入图片描述
\

1. 体验Stream流

  • 案例需求
    按照下面的要求完成集合的创建和遍历

    • 创建一个集合,存储多个字符串元素
    • 把集合中所有以"张"开头的元素存储到一个新的集合
    • 把"张"开头的集合中的长度为3的元素存储到一个新的集合
    • 遍历上一步得到的集合
  • 原始方式示例代码

public class StreamDemo {
	public static void main(String[] args) {
	
	//创建一个集合,存储多个字符串元素
	ArrayList<String> list = new ArrayList<String>();
	list.add("刘亦菲");
	list.add("宋祖儿");
	list.add("林黛玉");
	list.add("江疏影");
	list.add("张敏");
	list.add("张无忌");
	
	//把集合中所有以"张"开头的元素存储到一个新的集合
	ArrayList<String> zhangList = new ArrayList<String>();
	for(String s : list) {
		if(s.startsWith("张")) {
			zhangList.add(s);
		}
	}
	
	// System.out.println(zhangList);
	//把"张"开头的集合中的长度为3的元素存储到一个新的集合
	ArrayList<String> threeList = new ArrayList<String>();
	for(String s : zhangList) {
		if(s.length() == 3) {
			threeList.add(s);
		}
	}
	
	// System.out.println(threeList);
	//遍历上一步得到的集合
	for(String s : threeList) {
		System.out.println(s);
	}
	System.out.println("--------");
	
	//Stream流来改进
	// list.stream().filter(s -> s.startsWith("张")).filter(s ->
	s.length() == 3).forEach(s -> System.out.println(s));
	list.stream().filter(s -> s.startsWith("张")).filter(s -> s.length()
	== 3).forEach(System.out::println);
	}
}

\

使用Stream流示例代码

public class StreamDemo {
	public static void main(String[] args) {
		//创建一个集合,存储多个字符串元素
		ArrayList<String> list = new ArrayList<String>();
		list.add("刘亦菲");
		list.add("宋祖儿");
		list.add("林黛玉");
		list.add("江疏影");
		list.add("张敏");
		list.add("张无忌");
		
		//Stream流来改进
		list.stream().filter(s -> s.startsWith("张")).filter(s -> s.length()
		== 3).forEach(System.out::println);
		}
}

\

  • Stream流的好处
  • 直接阅读代码的字面意思即可完美展示无关逻辑方式的语义:获取流、过滤姓张、过滤长度
    为3、逐一打印
  • Stream流把真正的函数式编程风格引入到Java中
  • 代码简洁

\

2. Stream流的常见生成方式

  • Stream流的三类方法

    • 获取Stream流

      • 创建一条流水线,并把数据放到流水线上准备进行操作
    • 中间方法

      • 流水线上的操作
      • 一次操作完毕之后,还可以继续进行其他操作
    • 终结方法

      • 一个Stream流只能有一个终结方法
      • 是流水线上的最后一个操作

\

  • 生成Stream流的方式(获取流)

    • Collection体系集合

      • 使用默认方法stream()生成流, default Stream stream()
    • Map体系集合

      • 把Map转成Set集合,间接的生成流
    • 数组

      • 通过Arrays中的静态方法stream生成流
    • 同种数据类型的多个数据

      • 通过Stream接口的静态方法of(T… values)生成流

\

  • 代码演示
public class StreamDemo {
	public static void main(String[] args) {
		//Collection体系的集合可以使用默认方法stream()生成流
		List<String> list = new ArrayList<String>();
		Stream<String> listStream = list.stream();
		Set<String> set = new HashSet<String>();
		Stream<String> setStream = set.stream();
		
		//Map体系的集合间接的生成流
		Map<String,Integer> map = new HashMap<String, Integer>();
		Stream<String> keyStream = map.keySet().stream();
		Stream<Integer> valueStream = map.values().stream();
		Stream<Map.Entry<String, Integer>> entryStream =
		map.entrySet().stream();
		
		//数组可以通过Arrays中的静态方法stream生成流
		String[] strArray = {"hello","world","java"};
		Stream<String> strArrayStream = Arrays.stream(strArray);
		
		//同种数据类型的多个数据可以通过Stream接口的静态方法of(T... values)生成流
		Stream<String> strArrayStream2 = Stream.of("hello", "world",
		"java");
		Stream<Integer> intStream = Stream.of(10, 20, 30);
	}
}

\

3. Stream流中间操作方法【应用】

  • 概念
    中间操作的意思是,执行完此方法之后,Stream流依然可以继续执行其他操作
  • 常见方法
    在这里插入图片描述
    \

代码演示
Java8 - Stream

\

4. Stream流终结操作方法【应用】

  • 概念
    终结操作的意思是,执行完此方法之后,Stream流将不能再执行其他操作
  • 常见方法

在这里插入图片描述

  • 代码演示
public class StreamDemo {
	public static void main(String[] args) {
		//创建一个集合,存储多个字符串元素
		ArrayList<String> list = new ArrayList<String>();
		list.add("刘亦菲");
		list.add("宋祖儿");
		list.add("林黛玉");
		list.add("江疏影");
		list.add("张敏");
		list.add("张无忌");
		
		//需求1:把集合中的元素在控制台输出
		// list.stream().forEach(System.out::println);
		
		//需求2:统计集合中有几个以张开头的元素,并把统计结果在控制台输出
		long count = list.stream().filter(s -> s.startsWith("张")).count();
		System.out.println(count);
	}
}

\

5. Stream流的收集操作

  • 概念
    对数据使用Stream流的方式操作完毕后,可以把流中的数据收集到集合中
    Stream流里面不会改变集合数据源中的数据的,需要收集

  • 常用方法

    //	把结果收集到集合中
    R collect(Collector collector) 
    
  • 工具类Collectors提供了具体的收集方式
    在这里插入图片描述

  • 代码演示

    public class CollectDemo {
    	public static void main(String[] args) {
    		//创建List集合对象
    		List<String> list = new ArrayList<String>();
    		list.add("刘亦菲");
    		list.add("宋祖儿");
    		list.add("林黛玉");
    		list.add("江疏影");
    		/*
    		//需求1:得到名字为3个字的流
    		Stream<String> listStream = list.stream().filter(s -> s.length() ==
    		3);
    		
    		//需求2:把使用Stream流操作完毕的数据收集到List集合中并遍历
    		List<String> names = listStream.collect(Collectors.toList());
    		for(String name : names) {
    		System.out.println(name);
    		}
    		*/
    		
    		//创建Set集合对象
    		Set<Integer> set = new HashSet<Integer>();
    		set.add(10);
    		set.add(20);
    		set.add(30);
    		set.add(33);
    		set.add(35);
    		
    		/*
    		//需求3:得到年龄大于25的流
    		Stream<Integer> setStream = set.stream().filter(age -> age > 25);
    		//需求4:把使用Stream流操作完毕的数据收集到Set集合中并遍历
    		Set<Integer> ages = setStream.collect(Collectors.toSet())
    		for(Integer age : ages) {
    		System.out.println(age);
    		}
    		*/
    		
    		//定义一个字符串数组,每一个字符串数据由姓名数据和年龄数据组合而成
    		String[] strArray = {"刘亦菲,30", "宋祖儿,35", "林黛玉,33", "江疏影,25"};
    		
    		//需求5:得到字符串中年龄数据大于28的流
    		Stream<String> arrayStream = Stream.of(strArray).filter(s ->
    		Integer.parseInt(s.split(",")[1]) > 28);
    		
    		//需求6:把使用Stream流操作完毕的数据收集到Map集合中并遍历,字符串中的姓名作键,年龄作值
    		Map<String, Integer> map = arrayStream.collect(Collectors.toMap(s ->
    		s.split(",")[0], s -> Integer.parseInt(s.split(",")[1])));
    		Set<String> keySet = map.keySet();
    		for (String key : keySet) {
    			Integer value = map.get(key);
    			System.out.println(key + "," + value);
    		}
    	}
    }
    

\

在这里插入图片描述