【Java8】Java 中的 Stream 流收集器

目录

1、归约和汇总

2、分组

3、分区

4、理解收集器接口


        Java Stream 流用来帮助处理集合,类似于数据库中的操作。

        在 Stream 接口中,有一个抽象方法 collect,你会发现 collect 是一个归约操作(高级规约),就像 reduce 一样可以接受各种做法作为参数,将流中的元素累积成一个汇总结果。具体的做法可以通过Collector 接口来定义。// collect和reduce都是Stream接口中的汇总方法,collect方法接收一个Collector(收集器)作为参数

        收集器(Collector)非常有用,Collector 接口中方法的实现决定了如何对流执行归约操作//收集器用来定义收集器如何收集数据

        一般来说,Collector 会对元素应用一个转换函数,并将结果累积在一个数据结构中,从而产生这一过程的最终输出。

        Collectors 实用类提供了很多静态工厂方法,可以方便地创建常见收集器的实例,所以只要拿来用就可以了。最直接和最常用的收集器比如 toList、toSet、toMap 等静态方法。

1、归约和汇总

        使用 Collectors 进行规约和汇总,比如统计汇总,查找最大值和最小值,拼接字符串等。

        本节示例会使用到如下代码:

public class Dish {

    private final String name;
    private final boolean vegetarian;
    private final int calories;
    private final Type type;

    public Dish(String name, boolean vegetarian, int calories, Type type) {
        this.name = name;
        this.vegetarian = vegetarian;
        this.calories = calories;
        this.type = type;
    }

    public String getName() {
        return name;
    }

    public boolean isVegetarian() {
        return vegetarian;
    }

    public int getCalories() {
        return calories;
    }

    public Type getType() {
        return type;
    }

    public enum Type {MEAT, FISH, OTHER}

    @Override
    public String toString() {
        return name;
    }

    public static final List<Dish> menu = Arrays.asList(
            new Dish("pork", false, 800, Type.MEAT), 
            new Dish("beef", false, 700, Type.MEAT), 
            new Dish("chicken", false, 400, Type.MEAT), 
            new Dish("french fries", true, 530, Type.OTHER), 
            new Dish("rice", true, 350, Type.OTHER), 
            new Dish("season fruit", true, 120, Type.OTHER), 
            new Dish("pizza", true, 550, Type.OTHER), 
            new Dish("prawns", false, 400, Type.FISH), 
            new Dish("salmon", false, 450, Type.FISH));
}

        汇总操作:Collectors 类专门为汇总提供了一些工厂方法,用来满足各种类型的统计需要。

    public static void main(String[] args) {
        //1、计数
        Long count0 = menu.stream().collect(Collectors.counting());
        long count1 = menu.stream().count();

        //2、汇总和
        Integer summingInt = menu.stream().collect(Collectors.summingInt(Dish::getCalories));

        //3、求平均数
        Double averagingInt = menu.stream().collect(Collectors.averagingInt(Dish::getCalories));

        //4、一次性求:计数量、总和、最大值、最小值、平均值
        IntSummaryStatistics statistics = menu.stream().collect(Collectors.summarizingInt(Dish::getCalories));
        //使用统计后的值
        double average = statistics.getAverage();
        long sum = statistics.getSum();
        int max = statistics.getMax();
        int min = statistics.getMin();
        long count = statistics.getCount();
    }

        上述示例中,使用 summarizingInt 工方法返回的收集器功能很强大,通过一次 summarizing 操作你就可以统计到元素的个数,并得到总和、平均值、最大值和最小值

        查找流中的最大值和最小值Collectors.maxBy Collectors.minBy,来计算流中的最大或最小值。这两个收集器接收一个 Comparator 参数来比较流中的元素。

    public static void main(String[] args) {
        //比较器
        Comparator<Dish> comparator = Comparator.comparing(Dish::getCalories);
        //收集器
        Optional<Dish> collect = menu.stream().collect(Collectors.maxBy(comparator));
    }

        连接字符串joining 工厂方法返回的收集器会把对流中每一个对象应用 tostring 方法得到的所有字符串连接成一个字符串。如下所示:</

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

swadian2008

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值