Java 8 中的 Stream 是对集合(Collection)对象功能的增强,它专注于对集合对象进行各种非常便利、高效的聚合操作(aggregate operation),或者大批量数据操作 (bulk data operation)。

它提供串行和并行两种模式进行汇聚操作,并发模式能够充分利用多核处理器的优势,使用fork/join并行方式来拆分任务和加速处理过程。

前言

Stream 就如同一个迭代器(Iterator),单向,不可往复,数据只能遍历一次。

流的构成:
获取一个数据源(source)→ 数据转换 → 执行操作获取想要的结果。
每次转换原有 Stream 对象不改变,返回一个新的 Stream 对象(可以有多次转换)。 转换操作是lazy(惰性求值,只能迭代一次): 只有在Terminal操作执行时,才会一次性执行。 Stream 里有个操作函数的集合,每次转换操作就是把转换函数放入这个集合中。 在 Terminal 操作的时候循环 Stream 对应的集合,然后对每个元素执行所有的函数。

构造流的几种常见方法

1. Individual values

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

2. Arrays

	String [] strArray = new String[]{"a", "b", "c"};
stream = Stream.of(strArray);
stream = Arrays.stream(strArray); 3. Collections List<String> list = Arrays.asList(strArray);
stream = list.stream(); 文件生成流:
Stream<String> stream = Files.lines(Paths.get("data.txt"));

流转换为其它数据结构

1. Array

	String[] strArray1 = stream.toArray(String[]::new);

2. Collection

	List<String> list1 = stream.collect(Collectors.toList());
List<String> list2 = stream.collect(Collectors.toCollection(ArrayList::new));
Set set1 = stream.collect(Collectors.toSet());
Stack stack1 = stream.collect(Collectors.toCollection(Stack::new)); 3. String String str = stream.collect(Collectors.joining()).toString();

流的操作

当把一个数据结构包装成 Stream 后,就要开始对里面的元素进行各类操作了。常见的操作可以归类如下。

中间操作:
Intermediate(主要是打开流,做出某种程度的数据映射/过滤,然后返回一个新的流) map(mapToInt, flatMap)、
filter、 distinct、 sorted、
peek、 limit、 skip、 parallel、 sequential、 unordered .filter(person -> person.getAge() == 20) 过滤器 .distinct() 去除重复元素,这个方法是通过类的 equals 方法来判断两个元素是否相等的 .sorted()(流中的元素的类实现了 Comparable 接口) / sorted((p1, p2) -> p1.getAge() - p2.getAge()) 排序
.sorted(Comparator.comparingInt(Person::getAge)) .limit(long n) 返回前 n 个元素 .skip(long n) 去除前 n 个元素 .map(T -> R) 将流中的每一个元素 T 映射为 R(类似类型转换)
.map(Person::getName) .flatMap(T -> Stream<R>) 将流中的每一个元素 T(数组) 映射为一个流,再把每一个流连接成为一个流
.flatMap(Arrays::stream) 结束操作:
Terminal(流的最后一个操作) forEach、 forEachOrdered、
toArray、 reduce、 collect、 min、 max、
count、 anyMatch、 allMatch、 noneMatch、 findFirst、 findAny、 iterator boolean b = list.stream().anyMatch(person -> person.getAge() == 20); 判断是否有匹配条件的元素 .allMatch(T -> boolean) 是否所有元素都符合匹配条件 .reduce((T, T) -> T) 和 reduce(T, (T, T) -> T) 用于组合流中的元素,如求和,求积,求最大值等
.reduce(0, Integer::sum)
reduce 第一个参数 0 代表起始值为 0 .count() 返回流中元素个数,结果为 long 类型 .collect() 收集方法 最常用的方法,把流中所有元素收集到一个 List Set Collection 中 toList()
toSet()
toCollection()
toMap() joining() 连接字符串 counting() 计算总和

数值流

Stream<Integer> 类型,而每个 Integer 都要拆箱成一个原始类型再进行 sum 方法求和,这样大大影响了效率。

针对这个问题 Java 8 有良心地引入了数值流 IntStream, DoubleStream, LongStream。

三种对应的包装类型 Stream:

	IntStream、LongStream、DoubleStream

IntStream.of(new int[]{1, 2, 3}).forEach(System.out::println);

IntStream.range(1, 3).forEach(System.out::println);	半开区间[)

IntStream.rangeClosed(1, 3).forEach(System.out::println);	闭区间[]

流转换为数值流:
mapToInt(T -> int) : return IntStream
mapToDouble(T -> double) : return DoubleStream
mapToLong(T -> long) : return LongStream 数值流转换为流:
Stream<Integer> stream = intStream.boxed(); 数值流方法:
sum()
max()
min()
average()

并行流(必须是线程安全的)

Stream.of(list).parallel();

无限长度的流

generator:
generator方法,返回一个无限长度的Stream,其元素由Supplier接口的提供。 在Supplier是一个函数接口,只封装了一个get()方法,其用来返回任何泛型的值。 - generate(Supplier<T> s):返回一个无限长度的Stream 示例: 1. Stream<Double> generateA = Stream.generate(new Supplier<Double>() {
@Override
public Double get() {
return Math.random();
}
}); 2. Stream<Double> generateB = Stream.generate(()->Math.random());
3. Stream<Double> generateC = Stream.generate(Math::random); iterate
iterate方法,其返回的也是一个无限长度的Stream。 与generate方法不同的是,其是通过函数f迭代对给指定的元素种子而产生无限连续有序Stream,
其中包含的元素可以认为是:seed,f(seed),f(f(seed))无限循环。 - iterate(T seed, UnaryOperator<T> f) 示例: Stream.iterate(1, item -> item + 1).limit(10).forEach(System.out::println);
// 打印结果:1,2,3,4,5,6,7,8,9,10 上面示例,种子为1,也可认为该Stream的第一个元素,
通过f函数来产生第二个元素。
接着,第二个元素,作为产生第三个元素的种子,从而产生了第三个元素,
以此类推下去。
需要注意的是,该Stream也是无限长度的,
应该使用filter、limit等来截取Stream,否则会一直循环下去。

Stream(Java 8)的更多相关文章

  1. LeetCode算法题-Kth Largest Element in a Stream(Java实现)

    这是悦乐书的第296次更新,第315篇原创 01 看题和准备 今天介绍的是LeetCode算法题中Easy级别的第164题(顺位题号是703).设计一个类来查找流中第k个最大元素.请注意,它是排序顺序 ...

  2. 《大道至简》之第一章:编程的精义读后感(JAVA伪代码)

    ——大道至简之编程的精义读后感(JAVA伪代码) import.java.大道至简.*; import.java.愚公移山.*; public class YuGongYiShan{ 愚公 = {项目 ...

  3. Selenium关键字驱动测试框架Demo(Java版)

    Selenium关键字驱动测试框架Demo(Java版)http://www.docin.com/p-803493675.html

  4. [转]有哪些值得关注的技术博客(Java篇)

    有哪些值得关注的技术博客(Java篇)   大部分程序员在自学的道路上不知道走了多少坑,这个视频那个网站搞得自己晕头转向.对我个人来说我平常在学习的过程中喜欢看一些教程式的博客.这些博客的特点: 1. ...

  5. 网页爬虫的设计与实现(Java版)

    网页爬虫的设计与实现(Java版)     最近为了练手而且对网页爬虫也挺感兴趣,决定自己写一个网页爬虫程序. 首先看看爬虫都应该有哪些功能. 内容来自(http://www.ibm.com/deve ...

  6. 查找附近网点geohash算法及实现 (Java版本号)

    參考文档: http://blog.csdn.net/wangxiafghj/article/details/9014363geohash  算法原理及实现方式 http://blog.charlee ...

  7. 使用maven根据JSON文件自动生成Java POJO类(Java Bean)源文件

    根据JSON文件自动生成Java POJO类(Java Bean)源文件 本文介绍使用程序jsonschema2pojo来自动生成Java的POJO类源文件,本文主要使用maven,其他构建工具请参考 ...

  8. 小米2017秋招真题——电话号码分身问题(Java版)

    原题描述如下: 通过对各个数字对应的英文单词的分析,可以发现一些规律: 字母Z为0独占,字母W为2独占,字母U为4独占,字母X为6独占,字母G为8独占: 在过滤一遍0.2.4.6.8后,字母O为1独占 ...

  9. 剑指Offer——回溯算法解迷宫问题(java版)

    剑指Offer--回溯算法解迷宫问题(java版)   以一个M×N的长方阵表示迷宫,0和1分别表示迷宫中的通路和障碍.设计程序,对任意设定的迷宫,求出从入口到出口的所有通路.   下面我们来详细讲一 ...

随机推荐

  1. python中二维数组的建立,输入和输出

    ''' for循环: for i in range(x,y,dir): pass 首先这个区间是左闭右开 其次dir在省略的情况下默认为1,就是每次加一,也可以指定 python的数组: python ...

  2. C++11之列表初始化

    1. 在C++98中,标准允许使用花括号{}来对数组元素进行统一的集合(列表)初始化操作,如:int buf[] = {0};int arr[] = {1,2,3,4,5,6,7,8}; 可是对于自定 ...

  3. 【网络】Vmware虚拟机下三种网络模式配置

    VMware虚拟机有三种网络模式,分别是Bridged(桥接模式).NAT(网络地址转换模式).Host-only(主机模式). VMware workstation安装好之后会多出两个网络连接,分别 ...

  4. redis集群-4

    redis集群原理 redis cluster在设计的时候,就考虑到了去中心化,去中间件,也就是说,集群中的每个节点都是平等的关系,都是对等的,每个节点都保存各自的数据和整个集群的状态.每个节点都和其 ...

  5. ip协议,IP,子网掩码,ping命令是什么

    ip协议: 定网络地址的协议叫ip协议,它定义的地址称之为ip地址,广泛采用的v4版本即ipv4,它规定网络地址由32位2进制表示 IP地址:是给每个连接在Internet上的主机分配的一个32bit ...

  6. win10配置 samba

    一.先確認Linux中smb正確配置可以使用命令smbclient -L //localhost/ 二.win10配置1.打開win10對smb1.0/cifs檔共用支援2.本地群組原則編輯,修改如下 ...

  7. Emgucv图像处理工具

    此工具是当年自己在学习Emgucv的时候,慢慢积累的,包含了常用的图像处理算法,非常适合新人学习,现放出源码,由于是以前做的,功能不全. 当时Emgucv的学习资料非常之少,没有一本书是讲Emgucv ...

  8. PAT甲级——1147 Heaps【30】

    In computer science, a heap is a specialized tree-based data structure that satisfies the heap prope ...

  9. 一,Jetty启动

    一,Jetty安装 从官网download.eclipse.org/jetty/ 下载需要的版本,在指定目录解压即可,下面用$JETTY_HOME表示Jetty的解压目录,也就是安装目录.我用的版本是 ...

  10. Xshell与securecrt对比

    一.功能对比1.Xshell功能- 支持布局切换- 可调整Script执行顺序- 提供多标签功能- 对linux支持度高- 支持IPv6- 全球用户的多语言支持- 支持用户定义的键映射- 灵活和强大的 ...