java8之stream流

基本概念

流的含义

流:水流,IO流,数据流,指通过顺序/并行的方式将一个集合进行处理,得到新的集合。处理过程中,原来的流保持不变。


创建stream流的方式

	@Test
    public void testStream1(){
        /**
         * 创建stream
         * 1、使用Collection.stream()获取串行流
         */
        ArrayList<String> list = new ArrayList<>();
        Stream<String> stream = list.stream();
        /**
         * 2、使用Collection.parallelStream()获取并行流
         */
        Stream<String> parallelStream = list.parallelStream();

        /**
         * 3、通过Arrays.stream()获取数组流
         */
        String[] strings = new String[100];
        Stream<String> stringStream = Arrays.stream(strings);

        /**
         * 4、通过Stream.of()创建流
         */
        Stream.of("aaa","bbb","ccc");
        /**
         * 5、迭代创建无限流
         */
        Stream<Integer> iterate = Stream.iterate(0, x -> x + 2);
        iterate.limit(10)
                .forEach(System.out::println);
        System.out.println("generator");
        /**
         * 6、gengrator创建无限流
         */
        Stream<Double> generate = Stream.generate(() -> Math.random());
        generate.limit(100)
                .forEach(System.out::println);
    }

demo

List<Employee> employees = Arrays.asList(
            new Employee("zhangsan",33,33.333),
            new Employee("lisi",34,33333.333),
            new Employee("wangwu",334,3333.333),
            new Employee("songliu",3344,333.333),
            new Employee("songliu",3344,333.333),
            new Employee("songliu",3344,333.333),
            new Employee("songliu",3344,333.333)
    );

流使用-筛选与切片

filter : 接受一个lambda 进行过滤
limit : 截断流,使之不会超过指定数量
skip: 跳过流,跳过指定数量,跟limit互补
distinct: 去重,根据equals和hashcode去重

filter

	@Test
    public void testStream2(){
        Stream<Employee> stream = employees.stream()
                .filter(e -> e.getAge() > 35);
        stream.forEach(System.out::println);
    }

在这里插入图片描述

limit

	@Test
    public void testStream3(){
        employees.stream()
                .limit(2)
                .forEach(System.out::println);
    }

在这里插入图片描述

skip

	@Test
    public void testStream4(){
        employees.stream()
                .skip(3)
                .forEach(System.out::println);
    }

在这里插入图片描述

distinct

	@Test
    public void testStream5(){
        employees.stream()
                .distinct()
                .forEach(System.out::println);
    }

在这里插入图片描述


流使用-映射

映射
* map:接收lambda,将元素转化为其他形式或提取信息。接受一个函数为参数,将参数应用到每个元素上并映射成一个新的元素。
* flatmap:接受一个函数为参数,将其中每个值都转换为一个流,再将所有流合并为同一个流。

map

	@Test
    public void testStream3(){
        List<String> list = Arrays.asList("aaa", "bbb", "ccc", "ddd", "eee");
        list.stream()
                .map((x)->x.toUpperCase())
                .forEach(System.out::println);
        System.out.println("========================");
        employees.stream()
                .map(Employee::getName)
                .forEach(System.out::println);
    }
}

在这里插入图片描述

flatMap

	@Test
    public void testStream4(){
        List<String> list = Arrays.asList("aaa", "bbb", "ccc", "ddd", "eee");
        Stream<Stream<Character>> stream = list.stream()
                .map(TestStream3::getCharacterStream);
        stream.forEach(t -> t.forEach(System.out::println));

        System.out.println("=============================");
        Stream<Character> characterStream = list.stream()
                .flatMap(TestStream3::getCharacterStream);
        characterStream.forEach(System.out::println);
    }

    public static Stream<Character> getCharacterStream(String string){
        ArrayList<Character> list = new ArrayList<>();
        for (char c : string.toCharArray()) {
            list.add(c);
        }
        return list.stream();
    }

a
a
a
b
b
b
c
c
c
d
d
d
e
e
e
=============================
a
a
a
b
b
b
c
c
c
d
d
d
e
e
e


流使用-排序

  • sorted(): 自然排序
    sorted(Comparator com): 定制排序

sorted()

	@Test
    public void testStream(){
        List<String> list = Arrays.asList("aa", "dd", "cc", "bb");
        list.stream().sorted().forEach(System.out::println);
    }

在这里插入图片描述

sorted(Comparator com)

	@Test
    public void testStream2(){
        employees.stream().sorted((x,y)-> Integer.compare(x.getAge(), y.getAge()))
                .forEach(System.out::println);
    }

在这里插入图片描述


流使用-查找与匹配

  • 查找与匹配
    * allMatch-是否匹配所有元素
    * anyMatch-是否匹配至少一个元素
    * noneMatch-是否无匹配元素
    * findFirst-返回第一个元素
    * fundAny - 返回随机一个元素
    * count-返回元素和
    * max-返回最大值
    * min-返回最小值

allMatch

	@Test
    public void testStream3(){
        boolean match = employees.stream()
                .allMatch(x -> x.getAge() > 30);
        System.out.println(match);
    }

false

anyMatch

	@Test
    public void testStream4(){
        boolean match = employees.stream()
                .anyMatch(x -> x.getAge() == 180);
        System.out.println(match);
    }

false

noneMatch

	@Test
    public void test5(){
        boolean b = employees.stream().noneMatch(x -> x.getAge() < 1);
        System.out.println(b);
    }

true

findFirst

    @Test
    public void test6(){
        Optional<Employee> first = employees.stream().skip(2).findFirst();
        System.out.println(first.get());
    }

Employee(name=钱五, age=185, salary=9999.0, status=null)

findAny

    @Test
    public void test7(){
        Optional<Employee> any = employees.stream().findAny();
        System.out.println(any.get());
    }

Employee(name=张三, age=18, salary=999.0, status=null)

count

    @Test
    public void test8(){
        long count = employees.stream().count();
        System.out.println(count);
    }

6

max

    @Test
    public void test9(){
        Optional<Employee> max = employees.stream()
                .max((x,y) -> Integer.compare(x.getAge(),y.getAge()));
        System.out.println(max);
    }

Optional[Employee(name=钱五, age=185, salary=9999.0, status=null)]

min

    @Test
    public void test10(){
        Optional<Employee> min = employees.stream()
                .min((x, y) -> Integer.compare(x.getAge(), y.getAge()));
        System.out.println(min);
    }

Optional[Employee(name=张三, age=18, salary=999.0, status=null)]


流使用-规约

reduce

reduce(T identity,BinaryOperator) 将元素反复结合为一个值

	@Test
    public void testStream(){
        List<Integer> list = Arrays.asList(1, 2, 3, 4, 5, 6, 7, 8, 9);
        Integer reduce = list.stream().reduce(1, (x, y) -> x + y);
        System.out.println(reduce);

        System.out.println("=========计算工资和=========");
        Optional<Double> optional = employees.stream().map(Employee::getSalary)
                .reduce(Double::sum);
        System.out.println(optional.get());
    }

46
========= 计算工资和 =========
41994.0


流使用-收集

collect-将流转换为其他形式,接受一个Collector接口实现,用于给Stream元素做汇总

	@Test
    public void testStream2(){
//        将员工名字收集到一个集合中
        List<String> list = employees.stream()
                .map(Employee::getName)
                .collect(Collectors.toList());
        list.forEach(System.out::println);
        System.out.println("-分割线-");
        Set<String> set = employees.stream()
                .map(Employee::getName)
                .collect(Collectors.toSet());
        set.forEach(System.out::println);
        System.out.println("-分割线:使用特殊集合存储-");
        LinkedList<String> collect = employees.stream()
                .map(Employee::getName)
                .collect(Collectors.toCollection(LinkedList::new));
        collect.forEach(System.out::println);

    }

张三
李四
钱五
宋六
孙七
孙七
王八
-分割线-
李四
钱五
孙七
张三
宋六
王八
-分割线:使用特殊集合存储-
张三
李四
钱五
宋六
孙七
孙七
王八

collect提供的Collectors使用

	@Test
    public void test2(){
        System.out.println("总数");
        Long aLong = employees.stream()
                .collect(Collectors.counting());
        System.out.println(aLong);
        System.out.println("平均值");
        Double collect = employees.stream()
                .collect(Collectors.averagingDouble(Employee::getSalary));
        System.out.println(collect);
        System.out.println("总和");
        Double aDouble = employees.stream().collect(Collectors.summingDouble(Employee::getSalary));
        System.out.println(aDouble);
        System.out.println("最大值");
        Optional<Employee> optional = employees.stream().collect(Collectors.maxBy((e, f) -> Double.compare(e.getSalary(), f.getSalary())));
        System.out.println(optional.get().getSalary());
        System.out.println("最小值");
        Optional<Double> collect1 = employees.stream().map(Employee::getSalary).collect(Collectors.minBy(Double::compare));
        System.out.println(collect1.get());
    }

总数
7
平均值
7427.571428571428
总和
51993.0
最大值
9999.0
最小值
999.0

分组

	@Test
    public void test3(){
        Map<Employee.Status, List<Employee>> map = employees.stream().collect(Collectors.groupingBy(Employee::getStatus));
        System.out.println(map);
    }

{FREE=[Employee{name=‘张三’, age=18, salary=999.0, status=FREE}, Employee{name=‘李四’, age=183, salary=9999.0, status=FREE}], BUSY=[Employee{name=‘钱五’, age=185, salary=9999.0, status=BUSY}, Employee{name=‘宋六’, age=184, salary=9999.0, status=BUSY}], VACATION=[Employee{name=‘孙七’, age=183, salary=9999.0, status=VACATION}, Employee{name=‘孙七’, age=183, salary=9999.0, status=VACATION}, Employee{name=‘王八’, age=128, salary=999.0, status=VACATION}]}

多级分组

@Test
    public void test4(){
        Map<Employee.Status, Map<String, List<Employee>>> map = employees.stream()
                .collect(Collectors.groupingBy(Employee::getStatus
                        , Collectors.groupingBy((e) ->
                                {
                                    if (e.getAge() < 20) {
                                        return "青年";
                                    } else {
                                        return "老年";
                                    }
                                }
                        )));
        System.out.println(map);
    }

{VACATION={老年=[Employee{name=‘孙七’, age=183, salary=9999.0, status=VACATION}, Employee{name=‘孙七’, age=183, salary=9999.0, status=VACATION}, Employee{name=‘王八’, age=128, salary=999.0, status=VACATION}]}, FREE={青年=[Employee{name=‘张三’, age=18, salary=999.0, status=FREE}], 老年=[Employee{name=‘李四’, age=183, salary=9999.0, status=FREE}]}, BUSY={老年=[Employee{name=‘钱五’, age=185, salary=9999.0, status=BUSY}, Employee{name=‘宋六’, age=184, salary=9999.0, status=BUSY}]}}

分区

    @Test
    public void test5(){
        Map<Boolean, List<Employee>> collect = employees.stream()
                .collect(Collectors.partitioningBy((e) -> e.getAge()>20));
        System.out.println(collect);
    }

{false=[Employee{name=‘张三’, age=18, salary=999.0, status=FREE}], true=[Employee{name=‘李四’, age=183, salary=9999.0, status=FREE}, Employee{name=‘钱五’, age=185, salary=9999.0, status=BUSY}, Employee{name=‘宋六’, age=184, salary=9999.0, status=BUSY}, Employee{name=‘孙七’, age=183, salary=9999.0, status=VACATION}, Employee{name=‘孙七’, age=183, salary=9999.0, status=VACATION}, Employee{name=‘王八’, age=128, salary=999.0, status=VACATION}]}

数据处理

	@Test
    public void test6(){
        DoubleSummaryStatistics collect = employees.stream()
                .collect(Collectors.summarizingDouble(Employee::getSalary));
        System.out.println(collect.getAverage());
        System.out.println(collect.getMax());
        System.out.println(collect.getSum());
        System.out.println(collect.getCount());
    }

7427.571428571428
9999.0
51993.0
7

连接字符串

	@Test
    public void test07(){
        String collect = employees.stream().map(Employee::getName).collect(Collectors.joining(",","111","000"));
        System.out.println(collect);
    }

111张三,李四,钱五,宋六,孙七,孙七,王八000八

Map遍历

map.forEach((k,v)->{
            v.forEach(System.out::println);
        });
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值