Java8新特性之Stream流(二)关键知识点

我们的第一篇文章,主要是通过一个Demo,让大家体验了一下使用流API的那种酣畅淋漓的感觉。如果你没有实践,我还是再次呼吁你动手敲一敲,自己实实在跑一遍上一篇的Demo。相信你的感受和理解也会随之加深的。继续探索流API的高级功能之前,我们先从接口级别全面了解一下流API,这个对于我们来说是至关重要的。接下来,我给大家准备了一张流API关键知识点的UML图。但是大家只需要花一两分钟,整理看一下就可以了,不需要记住,先有个印象,后面我给大家讲解一些关键的方法:

流API UML

流API UML

我先整体介绍一下:流API定义的几个接口,都是在java.util.stream包中的.其中上图中的BaseStream接口是最基础的接口,它提供了所有流都可以使用的基本功能:

战斗才刚刚开始!

现在是时候开始记忆一些知识了.

BaseStream详解:

1
2
3
4
5
6
7
8
9
10
11
public interface BaseStream> extends AutoCloseable {
    Iterator iterator();//line2
    Spliterator spliterator();//line3
    boolean isParallel();//line4
    S sequential();//line5
    S parallel();//line6
    S unordered();//line7
    S onClose(Runnable closeHandler);//line8
    @Override
    void close();//line10
}
  • Iterator iterator(); //line2
    获得流的迭代器,并返回对该迭代器的引用(终端操作)

  • Spliterator spliterator(); //line3
    获取流的spliterator,并返回其引用(终端操作)

  • boolean isParallel(); //line4
    如果调用流是一个并行流,则返回true;如果调用流是一个顺序流,则返回false。

  • S sequential(); //line5
    基于调用流,返回一个顺序流。如果调用流已经是顺序流了,就返回该流。(中间操作)

  • S parallel(); //line6
    基于调用流,返回一个并行流。如果调用流已经是并行流了,就返回该流。(中间操作)

  • S unordered(); //line7
    基于调用流,返回一个无序流。如果调用流已经是无序流了,就返回该流。(中间操作)

  • S onClose(Runnable closeHandler); //line8
    返回一个新流,closeHandler指定了该流的关闭处理程序,当关闭该流时,将调用这个处理程序。(中间操作)

  • void close(); //line10
    从AutoCloseable继承来的,调用注册关闭处理程序,关闭调用流(很少会被使用到)

“终端操作”&”中间操作”

细心的同学应该注意到了,BaseStream接口里面的很多方法都在最后标识了(终端操作)和(中间操作),它们之间的区别是非常重要的。

  • 终端操作 会消费流,这种操作会产生一个结果的,比如上面的 iterator()和 spliterator(),以及上一篇中提到的min()和max(),或者是执行某一种操作,比如上一篇的forEach(),如果一个流被消费过了,那它就不能被重用的。

  • 中间操作 中间操作会产生另一个流。因此中间操作可以用来创建执行一系列动作的管道。一个特别需要注意的点是:中间操作不是立即发生的。相反,当在中间操作创建的新流上执行完终端操作后,中间操作指定的操作才会发生。所以中间操作是延迟发生的,中间操作的延迟行为主要是让流API能够更加高效地执行。

“中间操作”的状态

流的中间操作,可以为分无状态操作有状态操作两种,在无状态操作中,在处理流中的元素时,会对当前的元素进行单独处理。比如:谓词过滤操作,因为每个元素都是被单独进行处理的,所有它和流中的其它元素无关,因此被称为无状态操作;而在有状态操作中,某个元素的处理可能依赖于其他元素。比如查找最小值,最大值,和排序,因为他们都依赖于其他的元素。因此为称为有状态操作。当需要进行并行处理流时,有状态的操作和无状态的区别是非常重要的,因为有状态操作可能需要几次处理才能完成,后面的文章我将会给大家详细地讲,现在只需要正常学习下去就可以了

另外,指出一点,如果大家了解泛型的话,应该知道,泛型的类型参数只能是引用类型,因此Stream操作的对象只能是引用类型的,不能用于基本类型。当然官方早已考虑到这一点了,前面你们看到的IntStream,LongStream,DoubleStream就是官方给我们提供的处理基本类型的流了。此处是不是应该给他们掌声!

Stream详解

在有了前面的那些知识作铺垫之后,学Stream接口应该会顺风顺水了。还是先看看Stream的详情先:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
public interface Stream extends BaseStream> {
   Stream filter(Predicate predicate);//line2
    Stream map(Function mapper);//line3
   IntStream mapToInt(ToIntFunction mapper);//line4
   LongStream mapToLong(ToLongFunction mapper);
   DoubleStream mapToDouble(ToDoubleFunction mapper);
    Stream flatMap(Function> mapper);
   IntStream flatMapToInt(Function mapper);
   LongStream flatMapToLong(Function mapper);
   DoubleStream flatMapToDouble(Function mapper);
   Stream distinct();
   Stream sorted();//line12
   Stream sorted(Comparator comparator);//line13
   Stream peek(Consumer action);
   Stream limit(long maxSize);
   Stream skip(long n);
   void forEach(Consumer action);//line17
   void forEachOrdered(Consumer action);//line18
   Object[] toArray();
   小结一下

这一篇主要是介绍了流API的一些关键方法,和一些关键的概念,虽然稍微枯燥了一点,但是,不能否认,全面地学习流API,会让你对流API的认识会更加的深刻,所以如果时间允许,请再认真读读这一篇文章吧,当然,也可以在实践中慢慢认识它们,但是,对于这些基本概念的知识,你越早掌握,对你的益处是更加大的。到此为止,流API的基础知识已经学完了,后面的几篇文章我们就要开始更加深入地理解和运用他们实现一起强有力的功能了!


发布于 2020-04-01 21:09:37
分享
海报
182
上一篇:Java8新特性之Stream流(三)缩减操作 下一篇:Java8新特性之Stream流(一)基础体验
目录

    推荐阅读

    忘记密码?

    图形验证码