Java 8流处理详解

一、初识流

1. 什么是流?

流是Java API的新成员,它允许你以声明性方式(类似SQL,只写做什么,不考虑怎么做)处理数据集合。流就是从支持数据处理操作的源生成的元素序列。源可以是集合、数组或IO资源,数据处理操作包括filter(过滤),map(映射),reduce(累积操作),find(查找),match(匹配),sort(排序)。流可以顺序执行,也可以并行执行。

2. 集合与流

集合是内存中的数据结构,静态地包含所有值。流是从数据源中不断读取数据的固定数据结构,动态地获取值。

和迭代器类似,流只能遍历一次。遍历完之后,流就被消费了。

3. 内部迭代与外部迭代

外部迭代是指用户手动写循环进行的迭代(如while,foreach),内部迭代是API内部提供的迭代,Stream库中内置了迭代,称为内部迭代。

Java 8流处理详解_第1张图片

 

4. 中间操作与终端操作

只有一个终端操作,终端操作之后就结束了,终端操作前面的操作都是中间操作。

Java 8流处理详解_第2张图片

 二、使用流

1. 筛选、切片和映射

筛选:

List ints = Arrays.asList(1, 3, 2, 4, 5, 6, 9, 8, 7);
ints.stream()
            .filter(i-> i%2==0)//过滤出偶数
            .forEach(System.out::println);

切片:

Java 9引入两个新方法,takeWhile和dropWhile。

假设一个数组已经排好序,现在要找出小于等于10的数字,如果使用filter,就会遍历整个数组,事实上,遇到第一个大于10的数就应该停止,这时候使用takeWhile,用法与filter一样。

dropWhile是takeWhile的补充,遍历时,遇到为false的元素丢弃,当遇到第一个为true的元素就返回。

映射:

//Student类有id,name,age属性,现有List list
List names= list.stream
                        .map(Student::getName)
                        .collect(toList());

将Student映射为name。

流的扁平化flatMap:设有字符串数组["Hello","World"],现在要返回不含重复字符的字符数组[H,e,l,o,W,r,d]

Java 8流处理详解_第3张图片

 这样写只能对单词和单词之间进行去重。

Java 8流处理详解_第4张图片

 使用map将每个单词切分为一个个字符,flatMap将多个流合并为一个流,然后去重。

Java 8流处理详解_第5张图片

2. 查询和匹配

 allMatch:所有元素都匹配

anyMatch:至少匹配一个元素

noneMatch:全都不匹配返回true

findFirst:找到第一个符合的

findAny:找到任意一个符合的,效率比findFirst快。

3. 归约reduce

元素求和:

int sum=numbers.stream().reduce(0,(a,b)->a+b);

reduce的第一个参数是初始值,后面是方法参数和方法体

有状态的流和无状态的流

有无状态,主要看单次操作是否与之前操作有联系。

map、filter操作都是独立的,它们是无状态的流。

reduce,sum,max,sort,distinct等都需要保存之前的结果,并与当前结果对比,它们是有状态的流。

Java 8流处理详解_第6张图片

4. 数值流和对象流

mapToInt返回的是IntStream流(不同于Stream),还有mapToLong,mapToDouble等,一方面数值流可以避免空指针问题,另一方面避免拆箱装箱造成的性能损失。

数值流可以转换回对象流,intStream.boxed()

数值范围 IntStream.rangeClosed(1,100)  //从1到100

5. 构建流

(1)由值创建流  

Stream stream=Stream.of("a","b","cd","Action");

 空流Stream stream=Stream.empty();

(2) 由可空对象创建流

Stream home=Stream.ofNullable(System.getProperty("home"))

(3) 由数组创建流

Arrays.stream(arr)

(4) 由文件创建流

Java 8流处理详解_第7张图片

Files.lines会返回一个由指定文件中的各行构成的字符串流。

(5) 由函数生成流 :创建无限流

1)迭代

Java 8流处理详解_第8张图片

 创建了0,2,4,6,8,10......18共10个偶数。

如果没有加上limit,会一直创建下去。

2)生成

Java 8流处理详解_第9张图片

 生成了5个随机数。

参考:《Java实战》第2版

你可能感兴趣的:(Java学习,java,javascript)