java8 Stream 流快速入门

Java 8 中,得益于 lambda 带来的函数式编程,引入了一个全新的 Stream流 概念,用于解决集合已有的弊端。

好处

我们先来看一个例子:

筛选出 names 中以 ‘张’ 开头的字符串得到子集1,再筛选出 子集1 中长度为 3 的字符串,然后遍历输出。

// 传统集合的方式	
	public static void main(String[] args) {
        List<String> names = new ArrayList<>();
        names.add("张三丰");
        names.add("张大宝");
        names.add("张三");
        names.add("德玛杰");
        names.add("乔峰");
        names.add("李大宝");

        List<String> list1 = new ArrayList<>(); //以 '张' 开头的字符串
        for (String name:names){
            if (name.startsWith("张")){
                list1.add(name);
            }
        }

        List<String> list2 = new ArrayList<>(); // list1中长度为 3 的字符串
        for (String name:list1){
            if (name.length()==3){
                list2.add(name);
            }
        }

        for (String name:list2){
            System.out.println(name);
        }
    }
复制代码
// stream流方式	
	public static void main(String[] args) {
        List<String> names = new ArrayList<>();
        names.add("张三丰");
        names.add("张大宝");
        names.add("张三");
        names.add("德玛杰");
        names.add("乔峰");
        names.add("李大宝");

        names.stream().filter(name->name.startsWith("张"))
            .filter(name->name.length()==3).forEach(System.out::println);
    }
复制代码

可以看到用 stream 流方式比传统集合的方式精简了很多。

获取流的两种方式

  • 所有的 Collection 集合可以通过 stream() 方法获取流.
  • Stream 类的静态方法 of() 通常用于将数组转成 stream 流。
public static void main(String[] args) {
        // 集合转成 stream 流
        List<String> list = new ArrayList<>();
        Stream<String> listStream = list.stream();

        Set<Integer> set = new HashSet<>();
        Stream<Integer> setStream = set.stream();

        // 数组转成 stream 流
        String[] names = new String[]{"zs","ls","ww"};
        Stream<String> namesStream = Stream.of(names);

        Stream<Integer> integerStream = Stream.of(1, 2, 3, 4, 5);
    }
复制代码

方法分类

stream 流中方法分为两类:

  • 延迟方法,返回值仍是 Stream 类型
  • 终结方法,返回值不再是 Stream 类型,例如: count()forEach()

常用方法–fliter()

filter() 将一个流转换成另外一个子流,该方法接受一个 Predicate 类型的参数 (系统内置函数接口之一)。

Stream<T> filter(Predicate<? super T> predicate);

public static void main(String[] args) {
        List<String> names = new ArrayList<>();
        names.add("张三丰");
        names.add("张大宝");
        names.add("张三");
        names.add("德玛杰");
        names.add("乔峰");
        names.add("李大宝");
        
        // 过滤 names 集合,只要姓张的人,然后输出
        names.stream().filter(name->name.startsWith("张")).
        forEach(System.out::println);
    }
复制代码

Stream流特点–只能使用一次

Stream 流属于管道流, 只能被使用一次 ,当一个 Stream 流调用了终结方法后,就会被关闭, 再次调用其方法会报错

public static void main(String[] args) {
        // 数组转成 stream 流
        String[] names = new String[]{"zsf","ls","ww"};
        Stream<String> namesStream = Stream.of(names);

        namesStream.filter(name->name.length()==3).
            forEach(System.out::println);
        
        // 流已经被关闭,再次调用
        namesStream.forEach(System.out::println);
    }
复制代码
java8 Stream 流快速入门

常用方法–map()

如果需要将流中的元素映射到另一个流中,可以用 map() 方法,一般用于将一种类型的数据转成另一种类型的数据。

<R> Stream<R> map(Function<? super T, ? extends R> mapper);
复制代码
public static void main(String[] args) {
        // 数组转成 stream 流
        String[] strings = new String[]{"1","2","3"};
        Stream<String> stream1 = Stream.of(strings);

        // 使用 map 方法,将字符串类型的整数转成 Integer 类型的整数,然后遍历
        Stream<Integer> stream2 = stream1.map(k->Integer.parseInt(k));
        stream2.forEach(System.out::println);
        
        
    }
复制代码

常用方法–limit()

limit() 可以对流中的元素进行截取,只截取前 n 个

public static void main(String[] args) {
        // 数组转成 stream 流
        String[] strings = new String[]{"1","2","3","4"};

        // 只截取前3个元素,输出
        Stream.of(strings).limit(3).forEach(System.out::println);
    }
复制代码

常用方法–skip()

跳过流中的前 n 个元素,如果 n 大于流中元素的个数,返回一个长度为 0 的流。

public static void main(String[] args) {
        // 数组转成 stream 流
        String[] strings = new String[]{"1","2","3","4"};

        //  跳过前2个元素,输出
        Stream.of(strings).skip(2).forEach(System.out::println);
    }
复制代码

常用方法–concat()

Stream 类的静态方法用于将两个流合并。

public static void main(String[] args) {
        // 数组转成 stream 流
        String[] strings1 = new String[]{"1","2","3","4"};
        String[] strings2 = new String[]{"3","4","5","6"};

        Stream<String> stream1 = Stream.of(strings1);
        Stream<String> stream2 = Stream.of(strings2);

        Stream<String> stream3 = Stream.concat(stream1,stream2);
        stream3.forEach(System.out::println); // 输出 1,2,3,4,3,4,5,6
    }
复制代码

原文 

https://juejin.im/post/5f0171dcf265da23125895fb

本站部分文章源于互联网,本着传播知识、有益学习和研究的目的进行的转载,为网友免费提供。如有著作权人或出版方提出异议,本站将立即删除。如果您对文章转载有任何疑问请告之我们,以便我们及时纠正。

PS:推荐一个微信公众号: askHarries 或者qq群:474807195,里面会分享一些资深架构师录制的视频录像:有Spring,MyBatis,Netty源码分析,高并发、高性能、分布式、微服务架构的原理,JVM性能优化这些成为架构师必备的知识体系。还能领取免费的学习资源,目前受益良多

转载请注明原文出处:Harries Blog™ » java8 Stream 流快速入门

赞 (0)
分享到:更多 ()

评论 0

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址