Collectors.groupingBy是Java Stream实现SQL分组统计的核心工具,支持单/多级分组及计数、求和、平均值等嵌套聚合。

Java Stream 的 Collectors.groupingBy 是实现类 SQL 分组统计最常用、最直观的工具,它能将流中元素按指定键分组,并支持嵌套聚合(如计数、求和、平均值等),效果接近 GROUP BY + 聚合函数。
基础分组:模拟 GROUP BY
最简单的用法是按某个字段分组,生成 Map<k list>></k>,相当于 SQL 中的 GROUP BY column:
List<Person> people = Arrays.asList(
new Person("Alice", "Engineering", 8500),
new Person("Bob", "Marketing", 6200),
new Person("Charlie", "Engineering", 9100),
new Person("Diana", "Marketing", 7300)
);
// 按部门分组
Map<String, List<Person>> byDept = people.stream()
.collect(Collectors.groupingBy(Person::getDepartment));
// 结果:{"Engineering": [Alice, Charlie], "Marketing": [Bob, Diana]}
分组 + 计数:替代 COUNT(*)
用 Collectors.counting() 替代 SQL 的 COUNT(*),返回 Map<k long></k>:
Map<String, Long> countByDept = people.stream()
.collect(Collectors.groupingBy(Person::getDepartment, Collectors.counting()));
// 结果:{"Engineering"=2, "Marketing"=2}
分组 + 数值聚合:SUM / AVG / MAX / MIN
对数值字段做聚合时,配合 Collectors.summingDouble、Collectors.averagingDouble 等:
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
立即学习“Java免费学习笔记(深入)”;
-
工资总和(SUM):
Collectors.summingDouble(Person::getSalary) -
平均工资(AVG):
Collectors.averagingDouble(Person::getSalary) -
最高工资(MAX):
Collectors.maxBy(Comparator.comparingDouble(Person::getSalary))(返回Optional,需 map 处理) -
最低工资(MIN):同上,用
minBy
示例(部门平均工资):
Map<String, Double> avgSalaryByDept = people.stream()
.collect(Collectors.groupingBy(
Person::getDepartment,
Collectors.averagingDouble(Person::getSalary)
));
// 结果:{"Engineering"=8800.0, "Marketing"=6750.0}
多级分组 & 复合统计(类似 GROUP BY a, b)
用嵌套 groupingBy 实现多字段分组;再结合下游收集器实现复合统计:
// 按部门 + 是否高薪(>8000)双重分组,并统计人数
Map<String, Map<Boolean, Long>> grouped = people.stream()
.collect(Collectors.groupingBy(
Person::getDepartment,
Collectors.groupingBy(
p -> p.getSalary() > 8000,
Collectors.counting()
)
));
// 结果:{"Engineering"={true=2, false=0}, "Marketing"={true=0, false=2}}
也可以用 Collectors.toMap 或自定义对象封装更复杂的统计结果(如同时返回 count、sum、avg)。

















