1Stream Creation
有许多方法可以创建不同源的流实例。一旦创建,实例不会修改它的源,因此,允许从单个源创建多个实例。
(1)Empty Stream
这个empty()方法应用于创建空流,多用来防止流没有元素情况下返回null值


(2)Collection Stream
任何集合类似list,set都可以创建流

(3)Array Stream
数组也可以是stream的源,可以选择部分元素创建stream

(4)Stream.builder()
当使用builder 时应该在语句的右边部分另外指定所需的类型,否则建()方法将创建流<Object>:

(5)Stream.generate()
自定义长度(不要超出内存限制)

(6)Stream.iterate()
也可以使用iterate来创建流

(7)Primitives Stream
java8提供了三种基本类型:int,long ,Double,而Stream<T>泛型无法使用这些基本类型,于是就创建了三个新的特殊接口:IntStream, LongStream, DoubleStream.
使用新接口可以减少不必要的自动装箱,从而提高效率:


注意:
range(int startInclusive, int endExclusive)包含startInclusive元素,不包含endExclusive元素
rangeClosed(int startInclusive, int endInclusive)前后元素都包含
(8)String Stream
注意:JDK中没有CharStream ,而是用IntStream

(9)File Stream
Java中NIO包下的Files可以使用lines方法生成Steam,文本的每一行都成为流的一个元素

2 Stream 使用
在中断流之前可以一直使用该流,但是中断后在调用该流就会报IllegalStateException异常,因为因为流的设计是为了提供将有限的操作序列应用于函数样式中的元素源的能力,而不是存储元素。


要想重复使用需要做些更改

3Stream 管道
要对数据源的元素执行一系列操作并聚合它们的结果,需要三个部分--来源, 中间操作和一个终止操作。
中间操作返回一个新的修改后的流。例如,若要创建现有流的新流而不需要少数元素,则应采用skip()方法:

如果需要进行多个修改,则可以将中间操作链接起来。

流本身是毫无价值的,用户感兴趣的真实事物是终端操作的结果,终端操作可以是某种类型的值,也可以是应用于流的每个元素的操作。每个流只能使用一个终端操作

4Reduction Stream
API有许多Reduction 操作,例如,Count(),max(),min(),sum(), 但是这些操作根据预定义的实现工作,如果开发者自定义程序,可以使用reduce()和collect()方法
(1)reduce()方法,三个参数
identity :累加器的初始值,Stream为null或没有元素的情况下是个默认值
accumulator :指定元素聚合逻辑的函数
combiner :聚合累加器结果的函数
举栗子:



(2)collect()方法
举栗子:



average
averagingXX(), summingXX() 和summarizingXX()自动提供映射,不需要Map操作了

sum

statistical 信息:
可以从结果object 中获取acount, sum, min, averageby ,
方法getCount(), getSum(), getMin(), getAverage(), getMax().

Group

自定义collector

5并行流:
(1)API提供了parallel streams,可以在并行模式下操作

(2)如果流的源不是Collection 或 anarray,必须使用parallel()方法

(3)parallel模式转sequential 模式
