首页 > 编程语言 >Java 8新特性之Stream流

Java 8新特性之Stream流

时间:2023-06-02 11:44:57浏览次数:49  
标签:Java Stream stream Arrays integerList 元素 List 特性

Java8新特性之Stream流

什么是Stream流

Stream 使用一种类似用 SQL 语句从数据库查询数据的直观方式来提供一种对 Java 集合运算和表达的高阶抽象。 是一个来自数据源的元素队列并支持聚合操作

  1. 元素是特定类型的对象,形成一个队列。 Java中的Stream并不会存储元素,而是按需计算。
  2. 数据源 流的来源。 可以是集合,数组,I/O channel, 产生器generator 等。
  3. 聚合操作 类似SQL语句一样的操作, 比如filter, map, reduce, find, match, sorted等。

Stream特点

  • 无存储。Stream不是一种数据结构,它只是某种数据源的一个视图,数据源可以是一个数组,Java容器或I/O channel等。
  • 为函数式编程而生。对Stream的任何修改都不会修改背后的数据源,比如对Stream执行过滤操作并不会删除被过滤的元素,而是会产生一个不包含被过滤元素的新Stream。
  • 惰式执行。Stream上的操作并不会立即执行,只有等到用户真正需要结果的时候才会执行。
  • 可消费性。Stream只能被“消费”一次,一旦遍历过就会失效,就像容器的迭代器那样,想要再次遍历必须重新生成。

Stream流操作

1: 创建Stream

主要负责新建一个Stream流,或者基于现有的数组、List、Set、Map等集合类型对象创建出新的Stream流。

API 功能说明
stream() 创建出一个新的stream串行流对象
parallelStream() 创建出一个可并行执行的stream流对象
Stream.of() 通过给定的一系列元素创建一个新的Stream串行流对象

示例

    /**
     * 通过集合生成,应用中最常用的一种
     */
    List<Integer> integerList = Arrays.asList(1, 2, 3, 4, 5);
    Stream<Integer> stream1 = integerList.stream();

    /**
     * 通过数组生成
     */
    int[] intArr = new int[]{1, 2, 3, 4, 5};
    IntStream stream2 = Arrays.stream(intArr);


    /**
     * 创建并行流对象
     */
    Stream<Integer> promotionStream = integerList.parallelStream();

2: 中间管道

​ 负责对Stream进行处理操作,并返回一个新的Stream对象,中间管道操作可以进行叠加

API 功能说明
filter() 按照条件过滤符合要求的元素, 返回新的stream流
map() 将已有元素转换为另一个对象类型,一对一逻辑,返回新的stream流
flatMap() 将已有元素转换为另一个对象类型,一对多逻辑,即原来一个元素对象可能会转换为1个或者多个新类型的元素,返回新的stream流
limit() 仅保留集合前面指定个数的元素,返回新的stream流。limit的参数值必须>=0,否则将会抛出异常
skip() 跳过集合前面指定个数的元素,返回新的stream流。skip的参数值必须>=0,否则将会抛出异常
concat() 将两个流的数据合并起来为1个新的流,返回新的stream流
distinct() 对Stream中所有元素进行去重,返回新的stream流
sorted() 对stream中所有的元素按照指定规则进行排序,返回新的stream流
peek() 对stream流中的每个元素进行逐个遍历处理,返回处理后的stream流

示例:

filter()

    /**
    * filter筛选
    * 通过使用filter方法进行条件筛选,filter的方法参数为一个条件
    */
    List<Integer> integerList = Arrays.asList(1, 1, 2, 3, 4, 5);
    Stream<Integer> stream = integerList.stream().filter(i -> i > 3);

map()

主要用于List 循环获取Entity的属性值

    /**
    * map流映射(所谓流映射就是将接受的元素映射成另外一个元素)
    */
    List<String> stringList = Arrays.asList("str1", "str2", "str3", "str5");
    Stream<Integer> streams = stringList.stream().map(String::hashCode);

flatMap()

将已有元素转换为另一个对象类型,一对多逻辑

    /**
    * flatMap流转换(将一个流中的每个值都转换为另一个流)
    */
    List<String> wordList = Arrays.asList("Hello", "World");

    List<String> strList = wordList.stream()
    .map(w -> w.split("r"))
    .flatMap(Arrays::stream)
    .distinct()
    .collect(Collectors.toList());

limit()

    /**
    * limit返回指定流个数
    * 通过limit方法指定返回流的个数,limit的参数值必须>=0,否则将会抛出异常
    */
    List<String> wordList = Arrays.asList("Hello", "World","!");

    Stream<String> limitStream = wordList.stream().limit(1);

skip()

    /**
    * skip跳过流中的元素
    * 通过skip方法跳过流中的元素,例子中打印出来的数据: World,! 。skip的参数值必须>=0,否则将会抛出异常
    */
    List<String> wordList = Arrays.asList("Hello", "World","!");

    Stream<String> limitStream = wordList.stream().skip(1);

concat()

    Stream<String> streamOne = Stream.of("Hello");
    Stream<String> streamTwo = Stream.of("World");
    Stream<String> concatStream = Stream.concat(streamOne, streamTwo);

distinct()

    /**
    * distinct主要用来去重,以下代码片段使用 distinct 对元素进行去重
    */
    List<String> wordList = Arrays.asList("Hello", "World","!","Hello","!");

    Stream<String> limitStream = wordList.stream().distinct();

sorted()

        /**
         * sorted对流进行排序
         * sorted 方法用于对流进行排序。以下代码片段使用 sorted 方法进行排序
         */
        List<Integer> integerList = Arrays.asList(1, 3,2,10,7);
        Stream<Integer> sortedStream = integerList.stream().sorted();

        /**
         * 通过比较器比较
         */
        List<String> wordList = Arrays.asList("Hello", "World","!","Hello","!");
        wordList.stream().sorted(((str1, str2) -> {
            if (str1.length()> str2.length()) {
                return -1;
            } else {
                return 1;
            }
        }));

peek()

        /**
         * peek()属于中间方法,没有结束
         * peek只能作为管道中途的一个处理步骤,而没法直接执行得到结果,其后面必须还要有其它终止操作的时候才会被执行
         */
        List<String> wordList = Arrays.asList("Hello World!");
        //没有输出
        wordList.stream().peek(sentence -> System.out.println(sentence));
        //输出结果
        wordList.stream().peek(sentence -> System.out.println(sentence)).count();

3: 终止管道

​ 通过终止管道操作之后,Stream流将会结束,最后可能会执行某些逻辑处理,或者是按照要求返回某些执行后的结果数据

API 功能说明
count() 返回stream处理后最终的元素个数
max() 返回stream处理后的元素最大值
min() 返回stream处理后的元素最小值
findFirst() 找到第一个符合条件的元素时则终止流处理
findAny() 找到任何一个符合条件的元素时则退出流处理,这个对于串行流时与findFirst相同,对于并行流时比较高效,任何分片中找到都会终止后续计算逻辑
anyMatch() 返回一个boolean值,类似于isContains(),用于判断是否有符合条件的元素
allMatch() 返回一个boolean值,用于判断是否所有元素都符合条件
noneMatch() 返回一个boolean值, 用于判断是否所有元素都不符合条件
collect() 将流转换为指定的类型,通过Collectors进行指定
toArray() 将流转换为数组
iterator() 将流转换为Iterator对象
foreach() 无返回值,对元素进行逐个遍历,然后执行给定的处理逻辑

count()

count用来统计流中的元素个数。

        /**
         * 统计流中元素个数
         * 通过使用count方法统计出流中元素个数
         */
        List<String> wordList = Arrays.asList("Hello","World","!!");
        long count = wordList.stream().count();

max()/min()

获取流中最小最大值

        List<Integer> integerList = Arrays.asList(100,111,22,3,343);
        Optional<Integer> min = integerList.stream().min(Integer::compareTo);
        Optional<Integer> max = integerList.stream().max(Integer::compareTo);

findFirst()

查找大于100的第一个值

		  /**
         * 查询列表中大于100的数值
         */
        List<Integer> integerList = Arrays.asList(100,111,22,3,343);
        Optional<Integer> result = integerList.stream().filter(v -> v > 100).findFirst();

findAny()

找到任何一个符合条件的元素时则退出流处理

        List<Integer> integerList = Arrays.asList(100,343,22,3,111);
        Optional<Integer> result = integerList.stream().filter(v -> v > 100).findAny();
        System.out.println(result.get());

anyMatch()

		  /**
         * 查询列表中是否包含111的字符串
         */
        List<String> integerList = Arrays.asList("100", "343","22","3","111");
        boolean b = integerList.stream().anyMatch("111"::equals);

allMatch()

这个和anyMatch() 的类似,列表里面的元素都要匹配上。

noneMatch()

这个和anyMatch() 的类似,列表里面的元素都不能匹配上。

剩下的都是一些比较简单的,这里不在进行举例了。

优势和劣势

相对于foreach的方式,Stream有很多优势:

  1. 代码简洁,逻辑清洗
  2. 函数式接口,延迟执行的特性,中间管道操作不管有多少步骤都不会立即执行,只有遇到终止操作的时候才会开始执行,可以避免一些中间不必要的操作消耗
  3. 并行流场景效率会比迭代器逐个循环更高

劣势:

  1. 代码调试不是很方便
  2. 开发者需要去适应这种模式

以上就是本篇文章的所有内容,请大家多多指教。

标签:Java,Stream,stream,Arrays,integerList,元素,List,特性
From: https://www.cnblogs.com/zwhdd/p/17448911.html

相关文章

  • java爬虫详解及简单实例
    java爬虫是一种自动化程序,可以模拟人类在互联网上的行为,从网站上抓取数据并进行处理。下面是Java爬虫的详细解释:1、爬虫的基本原理Java爬虫的基本原理是通过HTTP协议模拟浏览器发送请求,获取网页的HTML代码,然后解析HTML代码,提取需要的数据。爬虫的核心是HTTP请求和HTML解析。2......
  • Java官方笔记4类和对象
    创建类定义类Bicycle:publicclassBicycle{//theBicycleclasshas//threefieldspublicintcadence;publicintgear;publicintspeed;//theBicycleclasshas//oneconstructorpublicBicycle(intstartCadence,intstar......
  • java爬虫详解及简单实例
    java爬虫是一种自动化程序,可以模拟人类在互联网上的行为,从网站上抓取数据并进行处理。下面是Java爬虫的详细解释:1、爬虫的基本原理Java爬虫的基本原理是通过HTTP协议模拟浏览器发送请求,获取网页的HTML代码,然后解析HTML代码,提取需要的数据。爬虫的核心是HTTP请求和HTML解析。2、爬虫......
  • 工作记录:Skywalking 对Java服务进行日志分析指标收集
    版本号:8.9.0目标:通过日志分析生成日志对应级别指标,skywalking页面展示指标采集情况,并配置指标规则告警到钉钉分析前提:skywalking已收集到对应服务的日志,日志列表可查询到服务日志1.日志分析指标配置Application配置修改config/application.yamllog-analyzer:selector:$......
  • java 如何保留小数位的0?(#.##与0.00的区别)
    1.情景展示如上图所示,在java语言中,如果后面的小数位是零的话,会被自动抹除。但在实际场景中,我们往往需要对小数位进行管理(统一展示小数的位数):不足小数位的进行补零操作,多余的小数位进行舍弃或者四舍五入。具体应如何实现?2.具体分析通过DecimalFormat.format()方法实现。3......
  • 怎么创建Java项目并在项目下创建包再创建类
    1. 如何创建Java项目?第一步:打开idea,选中Create New Project第二步:选择Java项目,选择配置好的JDK环境,选中JavaEE版本为JavaEE8,然后点Next第三步:啥也不点,直接点Next第四步:填你的项目名称(根据需求命名),选项目路径,点击Finish,完成项目创建到这里,一个简单的Java项目就创建完毕了!接下来我......
  • maven高级特性
    一、资源配置、资源加载属性值  之后打包,在打包的jar包中看属性:二、多环境配置,有些配置在测试环境 ......
  • JavaScript中的循环(6个)
    LoopesforwhiledowhileforofforEachforin1.forfor(initialization,condition,increment/decrement){//codegoeshere}eg:for(leti=0;i<6;i++){console.log(i)}2.whileUsingthewhileloopwhenwedonotknowhowmanitera......
  • ENVI 5.7/IDL 8.9 新特性介绍
    1ENVI5.7新特性ENVI5.7/IDL8.9于2023年5月正式发布,ENVI具备如下新增和改进的特性:新增支持数据类型新增支持SAR数据FLAASH模块更新全新变化检测工作流 工具箱部分工具更新全新交互式视域分析工具新增菜单和操作选项新增ENVITasksNITF更新新增......
  • 6.2java上课用
    packagexu01;publicclassxch2extendsThread{ publicxch2(Stringname,intpriorty){ super(name); this.setPriority(priorty); } publicvoidrun() {System.out.println(this.getName()+"正在执行"); try{ Thread.sleep(1000);//让线程休眠1秒钟,然后再出现异常 }cat......