Java8中Collectors的使用

前言: 基本类型的流没有这个用法

averagingDouble,averagingInt,averagingLong

平均值计算,返回的都是Double类型

        List<Dog> users = Arrays.asList(
                new Dog("a",9),
                new Dog("b",10),
                new Dog("c",10),
                new Dog("d",13),
                new Dog("e",14));

        Double collect = users.stream().collect(Collectors.averagingDouble(x -> x.getAge()));
        System.out.println(collect);//11.2
        Double collect1 = users.stream().collect(Collectors.averagingInt(x -> x.getAge()));
        System.out.println(collect1);//11.2
        Double collect2 = users.stream().collect(Collectors.averagingLong(x -> x.getAge()));
        System.out.println(collect2);//11.2

collectingAndThen

List<Dog> users = Arrays.asList(
                new Dog("a",9),
                new Dog("b",10),
                new Dog("c",10),
                new Dog("d",13),
                new Dog("e",14));

        Map<Integer, Long> collect = users.stream().collect(Collectors.groupingBy(x -> x.getAge(), Collectors.counting()));
        System.out.println(collect);//{9=1, 10=2, 13=1, 14=1}
        Integer collect1 = users.stream().collect(Collectors.collectingAndThen(Collectors.groupingBy(x -> x.getAge()), map -> map.size()));
        System.out.println(collect1);//4
  • 第一个参数为要做的操作,第二个参数对第一个参数收集到的结果进行如何的处理

counting

        //创建数组 元素为0~9
        List<Integer> collect = Stream.iterate(0, x -> x + 1).limit(10).collect(Collectors.toList());

        Long collect1 = collect.stream().collect(Collectors.counting());
        System.out.println(collect1);

groupingBy

  1. 一个参数表示按照哪个值来分组,这个值为key,其中的value就为符合k的集合
  2. 两个参数表示:第一个参数同上,第二个参数可以对value集合再次进行流操作
  3. 三个参数表示:第一个参数同上,第二个参数表示要返回什么样的Map,第三个参数可以对value集合再次进行流操作
        List<Dog> users = Arrays.asList(
                new Dog("a",9),
                new Dog("b",10),
                new Dog("c",10),
                new Dog("d",13),
                new Dog("e",14));
        //按照年龄来分类,key为年龄,value为相同年龄的集合
        Map<Integer, List<Dog>> collect = users.stream().collect(Collectors.groupingBy(x -> x.getAge()));
        //{9=[Dog{name='a', age=9}], 10=[Dog{name='b', age=10}, Dog{name='c', age=10}], 13=[Dog{name='d', age=13}], 14=[Dog{name='e', age=14}]}
        System.out.println(collect);
        //{9=[], 10=[Dog{name='c', age=10}], 13=[], 14=[]}
        Map<Integer, Set<Dog>> c = users.stream().collect(Collectors.groupingBy(x -> x.getAge(), Collectors.filtering(x -> x.getName().equals("c"), Collectors.toSet())));
        //
        TreeMap<Object, Set<Dog>> collect1 = users.stream().collect(Collectors.groupingBy(x -> x.getAge(), TreeMap::new, Collectors.toSet()));
        System.out.println(collect1);

groupingByConcurrent

使用同groupingBy,但是返回的是线程安全的集合。

joining

          String[] strings = {"gs","sb","dpz"};
        String collect = Arrays.stream(strings).collect(Collectors.joining());
        String collect1 = Arrays.stream(strings).collect(Collectors.joining(","));
        String collect2 = Arrays.stream(strings).collect(Collectors.joining(",", "[", "]"));
        System.out.println(collect);//gssbdpz
        System.out.println(collect1);//gs,sb,dpz
        System.out.println(collect2);//[gs,sb,dpz]

mapping

        //创建数组 元素为0~9
        List<Integer> collect = Stream.iterate(0, x -> x + 1).limit(10).collect(Collectors.toList());

        //过滤
        Set<Integer> collect1 = collect.stream().collect(Collectors.mapping(x -> x, Collectors.toSet()));
        //等价于
        Set<Integer> collect2 = collect.stream().map(x -> x).collect(Collectors.toSet()); 

maxBy,minBy

  1. maxBy:return (a, b) -> comparator.compare(a, b) >= 0 ? a : b 如果返回的小于0,取b
  2. minBy:return (a, b) -> comparator.compare(a, b) <= 0 ? a : b 如果返回结果小于0,取a
 //创建数组 元素为0~9
        List<Integer> collect = Stream.iterate(0, x -> x + 1).limit(10).collect(Collectors.toList());

        Optional<Integer> collect1 = collect.stream().collect(Collectors.maxBy((x, y) -> -1));
        Optional<Integer> collect2 = collect.stream().collect(Collectors.minBy((x, y) -> -1));
        System.out.println(collect1); //9
        System.out.println(collect2); //0

partitioningBy

1.一个参数: 根据过滤把结果集分为两组存在Map中,键为true的为一组,键为false的为一组,值为List存放元素
2. 两个参数:同上,但是第二个参数表示再次过滤Map中的Value。

 //创建数组 元素为0~9
        List<Integer> collect = Stream.iterate(0, x -> x + 1).limit(10).collect(Collectors.toList());

        Map<Boolean, List<Integer>> collect2 = collect.stream().collect(Collectors.partitioningBy(x -> x > 2));
        System.out.println(collect2); // {false=[0, 1, 2], true=[3, 4, 5, 6, 7, 8, 9]}
        Map<Boolean, Integer> collect1 = collect.stream().collect(Collectors.partitioningBy(x -> x > 2, Collectors.reducing(0,(x, y) -> Math.min(x, y))));
        System.out.println(collect1); // {false=0, true=0}

reducing

 //创建数组 元素为0~9
        List<Integer> collect = Stream.iterate(0, x -> x + 1).limit(10).collect(Collectors.toList());

        //因为提供了第一个参数,确定了类型,返回值为该类型对象,第二个参数x,y为流中的两个值进行操作
        Integer collect1 = collect.stream().collect(Collectors.reducing(0, (x, y) -> Math.min(x, y)));
        //返回值Optional<T>,第二个参数x,y为流中的两个值进行操作
        Optional<Integer> collect2 = collect.stream().collect(Collectors.reducing((x, y) -> Math.min(x, y)));
        //因为提供了第一个参数,确定了类型,返回值为该类型对象,第二个参数还可以对每个元素进行一次操作,第三个参数x,y为流中的两个值进行操作
        Integer collect3 = collect.stream().collect(Collectors.reducing(0, x -> x+1, (x, y) -> Math.max(x, y)));

summarizingDouble,summarizingInt,summarizingLong

方法描述
summarizingDouble(ToDoubleFunction<? super T> mapper)接口实现方法为传入一个当前元素,返回值为对应的基本类型,收集后得到一个xxxSummaryStatistics实例,属性包括最大,最小等属性
summarizingInt(ToIntFunction<? super T> mapper)同上
summarizingLong(ToLongFunction<? super T> mapper)同上
        //创建数组 元素为0~9
        List<Integer> collect = Stream.iterate(0, x -> x + 1).limit(10).collect(Collectors.toList());
        //Collectors.summarizingInt(ToIntFunction<? super T> mapper)
        IntSummaryStatistics collect1 = collect.stream().collect(Collectors.summarizingInt(x -> x));
        System.out.println(collect1);//IntSummaryStatistics{count=10, sum=45, min=0, average=4.500000, max=9}
        DoubleSummaryStatistics collect2 = collect.stream().collect(Collectors.summarizingDouble(x -> x));
        System.out.println(collect2);//DoubleSummaryStatistics{count=10, sum=45.000000, min=0.000000, average=4.500000, max=9.000000}
        LongSummaryStatistics collect3 = collect.stream().collect(Collectors.summarizingLong(x -> x));
        System.out.println(collect3);//LongSummaryStatistics{count=10, sum=45, min=0, average=4.500000, max=9}

summingDouble,summingInt,summingLong

方法描述
summingDouble(ToDoubleFunction<? super T> mapper)接口实现方法为传入一个当前元素,返回值为对应的基本类型,收集后得到一个对应的包装类,值就为和
summingInt(ToIntFunction<? super T> mapper)同上
summingLong(ToLongFunction<? super T> mapper)同上
        //创建数组 元素为0~9
        List<Integer> collect = Stream.iterate(0, x -> x + 1).limit(10).collect(Collectors.toList());
        //Collectors.summarizingInt(ToIntFunction<? super T> mapper)
        Double collect1 = collect.stream().collect(Collectors.summingDouble(x -> x));
        Integer collect2 = collect.stream().collect(Collectors.summingInt(x -> x));
        Long collect3 = collect.stream().collect(Collectors.summingLong(x -> x));

toCollection

        Integer[] a = {1,2,3,4,5,6,7,8,9,10};
        //Collectors.toCollection 返回指定集合类型,要求:必须为collectors的子类
        Arrays.stream(a).collect(Collectors.toCollection(TreeSet::new));
        Arrays.stream(a).collect(Collectors.toCollection(()->new TreeSet<>()));

toConcurrentMap

 Integer[] a = {1,2,3,4,5,6,7,8,9,10};
        //toConcurrentMap.toMap 使用
        //1.两个参数,一个key,一个value 组成任意Map(key,value的类型由返回值类型决定)
        //{1=1, 2=2, 3=3, 4=4, 5=5, 6=6, 7=7, 8=8, 9=9, 10=10}
        ConcurrentMap<String, String> collect = Arrays.stream(a).collect(Collectors.toConcurrentMap(x -> x.toString(), x -> x.toString()));
        //2.三个参数,第三个参数决定key冲突时怎么处理,(x,y) 代表两个冲突k的value值
        //{1=11} key全为1,value每次都保存最新的那个
        ConcurrentMap<String, String> collect1 = Arrays.stream(a).collect(Collectors.toConcurrentMap((x) -> "1", x -> String.valueOf(x+1),(x, y)->y));
        3.四个参数,第四个代表要返回的Map类型,默认ConcurrentMap,只允许ConcurrentMap的子类
        ConcurrentSkipListMap<String, String> collect2 = Arrays.stream(a).collect(Collectors.toConcurrentMap((x) -> "1", x -> String.valueOf(x + 1), (x, y) -> y, ConcurrentSkipListMap::new));

toList,toSet

 Integer[] a = {1,2,3,4,5,6,7,8,9,10,1};

        //去重,组成set [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
        Set<Integer> set = Arrays.stream(a).collect(Collectors.toSet());
        //直接组成list [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1]
        List<Integer> list = Arrays.stream(a).collect(Collectors.toList());

toMap

使用例子:

        Integer[] a = {1,2,3,4,5,6,7,8,9,10};
        //Collectors.toMap 使用
        //1.两个参数,一个key,一个value 组成任意Map(key,value的类型由返回值类型决定)
        //{1=1, 2=2, 3=3, 4=4, 5=5, 6=6, 7=7, 8=8, 9=9, 10=10}
        Map<String, String> collect = Arrays.stream(a).collect(Collectors.toMap(x -> x.toString(), x -> x.toString()));
        //2.三个参数,第三个参数决定key冲突时怎么处理,(x,y) 代表两个冲突k的value值
        //{1=11} key全为1,value每次都保存最新的那个
        Map<String, String> collect1 = Arrays.stream(a).collect(Collectors.toMap((x) -> "1", x -> String.valueOf(x+1),(x,y)->y));
        //3.四个参数,第四个代表要返回的Map类型,默认hashMap
        Map<String, String> collect2 = Arrays.stream(a).collect(Collectors.toMap((x) -> "1", x -> String.valueOf(x+1),(x,y)->y,TreeMap::new));
  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Java 8Collectors.toMap方法可以将Stream的元素转换为一个Map对象。该方法有三个参数:keyMapper,valueMapper和mergeFunction。其,keyMapper用于将Stream的元素转换为Map的key,valueMapper用于将Stream的元素转换为Map的value,mergeFunction用于处理当key重复时的冲突情况。 下面是一个例子,假设我们有一个List对象,其包含多个Person对象,每个Person对象都有一个唯一的id属性和一个name属性。我们可以使用Collectors.toMap方法将List转换为一个以id为key,以Person对象为value的Map对象: ```java List<Person> personList = new ArrayList<>(); // 假设我们已经将多个Person对象添加到了personList Map<Integer, Person> personMap = personList.stream() .collect(Collectors.toMap(Person::getId, Function.identity())); ``` 在上面的例子,Person::getId表示将Person对象的id属性作为Map的key,Function.identity()表示将Person对象本身作为Map的value。如果我们想要将Person对象的name属性作为Map的value,可以这样写: ```java Map<Integer, String> personMap = personList.stream() .collect(Collectors.toMap(Person::getId, Person::getName)); ``` 如果我们的List有重复的id,那么上面的代码将会抛出IllegalStateException异常。为了避免这种情况,我们可以使用mergeFunction参数来处理冲突。例如,如果我们想要将重复的id的Person对象合并为一个List,可以这样写: ```java Map<Integer, List<Person>> personMap = personList.stream() .collect(Collectors.toMap(Person::getId, Collections::singletonList, (list1, list2) -> { List<Person> resultList = new ArrayList<>(list1); resultList.addAll(list2); return resultList; })); ``` 在上面的代码Collections::singletonList表示将Person对象转换为只包含一个元素的List,mergeFunction参数则表示将两个List合并为一个List。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值