当前位置: 首页 > news >正文

Stream流的groupingBy

Stream流的groupingBy

简单使用

业务场景:现在有100个人,这些人都年龄分部在18-30岁之间。现要求把他们按照年龄进行分组
key:年龄
value:数据列表

public void listToMapGroup() {//这里假设通过listStreamService.list();方法查询了这100人List<Perple> list = perpleService.list();//按照age进行分组Map<Integer, List<Perple>> result = list.stream().collect(Collectors.groupingBy(Perple::getAge));//打印结果result.forEach((k, v) -> {System.out.println(k);System.out.println(v);System.out.println("--------------------");});
}

效果相当于是,把list这个集合里面存放的100个人每个人都调用Perple的getAge方法,按照getAge方法的返回值进行分组。每个组是一个Map<Integer, List>类型的对象。Map<Integer, List>的键是getAge的返回值,即,分组的依据。Map<Integer, List>的值是这个年龄对应组中的成员。

如果要进行排序

分组之后,是不能对每个分组进行比较的(也就无法排序),因为groupingBy是一个终结流。
Collectors.groupingBy(Function<? super T, ? extends K> classifier, Collector<? super T, A, D> downstream)
这里有两个思路:
1:提前排序,再进行分组
2:分组后,对Map进行处理,对其每个value排序

做法一:

提前排序,再进行分组.
这里还展示了一些groupingBy方法的扩展用法。

import com.alibaba.fastjson.JSONObject;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;public class Test {public static void main(String[] args) {Student student1 = new Student(1, 1);Student student2 = new Student(1, 1);Student student3 = new Student(2, 2);Student student4 = new Student(2, 3);Student student5 = new Student(3, 3);Student student6 = new Student(3, 4);Student student7 = new Student(4, 1);Student student8 = new Student(4, 1);Student student9 = new Student(4, 2);Student student10 = new Student(4, 1);List<Student> list = Arrays.asList(student1, student2, student3, student4, student5, student6, student7, student8, student9, student10);System.out.println("--------- 根据字段分组,求每个分组的sum ----------");Map<Integer, Integer> collect = list.stream().collect(Collectors.groupingBy(Student::getId, Collectors.summingInt(Student::getScore)));System.out.println(collect.toString());System.out.println("--------- 根据字段分组,求每个分组的count ----------");Map<Integer, Long> countMap = list.stream().collect(Collectors.groupingBy(Student::getId, Collectors.counting()));System.out.println(countMap.toString());System.out.println("--------- 根据字段分组,每个分组为:对象的指定字段 ----------");Map<Integer, List<Integer>> groupMap = list.stream().collect(Collectors.groupingBy(Student::getId, Collectors.mapping(Student::getScore, Collectors.toCollection(ArrayList::new))));System.out.println(groupMap.toString());System.out.println("--------- 根据字段分组,默认分组 ----------");Map<Integer, List<Student>> defaultGroupMap = list.stream().collect(Collectors.groupingBy(Student::getId));System.out.println(JSONObject.toJSONString(defaultGroupMap));System.out.println("--------- 根据字段分组,每个分组按照指定字段进行生序排序 ----------");Map<Integer, List<Student>> sortGroupMap = list.stream().sorted(Comparator.comparing(Student::getScore)).collect(Collectors.groupingBy(Student::getId));System.out.println(JSONObject.toJSONString(sortGroupMap));System.out.println("--------- 先排序,再分组 ----------");Map<Integer, List<Student>> reversedSortGroupMap = list.stream().sorted(Comparator.comparing(Student::getScore).reversed()).collect(Collectors.groupingBy(Student::getId));System.out.println(JSONObject.toJSONString(reversedSortGroupMap));}
}class Student {private Integer id;private Integer score;public Integer getId() {return id;}public void setId(Integer id) {this.id = id;}public Integer getScore() {return score;}public void setScore(Integer score) {this.score = score;}public Student(Integer id, Integer score) {this.id = id;this.score = score;}
}

执行结果:

--------- 根据字段分组,求每个分组的sum ----------
{1=2, 2=5, 3=7, 4=5}
--------- 根据字段分组,求每个分组的count ----------
{1=2, 2=2, 3=2, 4=4}
--------- 根据字段分组,每个分组为:对象的指定字段 ----------
{1=[1, 1], 2=[2, 3], 3=[3, 4], 4=[1, 1, 2, 1]}
--------- 根据字段分组,默认分组 ----------
{1:[{"id":1,"score":1},{"id":1,"score":1}],2:[{"id":2,"score":2},{"id":2,"score":3}],3:[{"id":3,"score":3},{"id":3,"score":4}],4:[{"id":4,"score":1},{"id":4,"score":1},{"id":4,"score":2},{"id":4,"score":1}]}
--------- 根据字段分组,每个分组按照指定字段进行生序排序 ----------
{1:[{"id":1,"score":1},{"id":1,"score":1}],2:[{"id":2,"score":2},{"id":2,"score":3}],3:[{"id":3,"score":3},{"id":3,"score":4}],4:[{"id":4,"score":1},{"id":4,"score":1},{"id":4,"score":1},{"id":4,"score":2}]}
---------  先排序,再分组  ----------
{1:[{"id":1,"score":1},{"id":1,"score":1}],2:[{"id":2,"score":3},{"id":2,"score":2}],3:[{"id":3,"score":4},{"id":3,"score":3}],4:[{"id":4,"score":2},{"id":4,"score":1},{"id":4,"score":1},{"id":4,"score":1}]}

做法二:

先分组,再排序。
先将数据进行groupingBy,得到Map<Long, List>
在通过forEach对每个List进行排序

        Map<Long, List<StreamMapEntity>> map = getMap();System.out.println("------ flatMap 处理Map<Long,List<StreamMapEntity>> ------");System.out.println();System.out.println("初始数据:" + JSONObject.toJSONString(map));System.out.println();map.keySet().forEach(key -> map.computeIfPresent(key, (k, v) -> v.stream().sorted(Comparator.comparing(StreamMapEntity::getId).reversed()).collect(Collectors.toList())));System.out.println("处理map:对map内的每个list进行排序:");System.out.println(JSONObject.toJSONString(map));

执行结果:

------ flatMap 处理Map<Long,List<StreamMapEntity>> ------初始数据:{1111:[{"id":1,"name":"aa"},{"id":2,"name":"bb"},{"id":3,"name":"cc"},{"id":4,"name":"dd"}],2222:[{"id":5,"name":"ee"},{"id":6,"name":"ff"},{"id":7,"name":"gg"},{"id":8,"name":"hh"}]}处理map:对map内的每个list进行排序:
{1111:[{"id":4,"name":"dd"},{"id":3,"name":"cc"},{"id":2,"name":"bb"},{"id":1,"name":"aa"}],2222:[{"id":8,"name":"hh"},{"id":7,"name":"gg"},{"id":6,"name":"ff"},{"id":5,"name":"ee"}]}

相关文章:

  • 100天精通风控建模(原理+Python实现)——第3天:风控建模中如何处理缺失值?
  • 如何有效的保护Windows登录 安当加密
  • Googletest(Gtest)使用case指南
  • Leetcode153. Find Minimum in Rotated Sorted Array
  • C语言进阶
  • Mybatis-plus 内部提供的 ServiceImpl<M extends BaseMapper<T>, T> 学习总结
  • 链表的实现(文末附完整代码)
  • shell之route命令介绍
  • Apipost-Helper:IDEA中的类postman工具
  • 数据结构—内部排序(上)
  • 为 Ubuntu 虚拟机构建 SSH 服务器
  • 【蓝桥杯选拔赛真题66】Scratch画图机器人 少儿编程scratch图形化编程 蓝桥杯创意编程选拔赛真题解析
  • 74hc595模块参考
  • 100127. 给小朋友们分糖果 II
  • asp.net core weapi 结合identity完成登录/注册/角色/权限分配
  • 【许晓笛】 EOS 智能合约案例解析(3)
  • 5分钟即可掌握的前端高效利器:JavaScript 策略模式
  • C++回声服务器_9-epoll边缘触发模式版本服务器
  • cookie和session
  • CSS盒模型深入
  • JavaScript工作原理(五):深入了解WebSockets,HTTP/2和SSE,以及如何选择
  • JavaWeb(学习笔记二)
  • Logstash 参考指南(目录)
  • MyEclipse 8.0 GA 搭建 Struts2 + Spring2 + Hibernate3 (测试)
  • webgl (原生)基础入门指南【一】
  • windows下如何用phpstorm同步测试服务器
  • 阿里云ubuntu14.04 Nginx反向代理Nodejs
  • 从0到1:PostCSS 插件开发最佳实践
  • 关于extract.autodesk.io的一些说明
  • 函数式编程与面向对象编程[4]:Scala的类型关联Type Alias
  • 浏览器缓存机制分析
  • 模型微调
  • 前端js -- this指向总结。
  • 微信小程序开发问题汇总
  • 一起来学SpringBoot | 第十篇:使用Spring Cache集成Redis
  • 由插件封装引出的一丢丢思考
  • # 深度解析 Socket 与 WebSocket:原理、区别与应用
  • ###项目技术发展史
  • #QT(智能家居界面-界面切换)
  • $L^p$ 调和函数恒为零
  • (附程序)AD采集中的10种经典软件滤波程序优缺点分析
  • (附源码)php投票系统 毕业设计 121500
  • (数位dp) 算法竞赛入门到进阶 书本题集
  • (转)菜鸟学数据库(三)——存储过程
  • .net FrameWork简介,数组,枚举
  • .net 设置默认首页
  • .NET框架设计—常被忽视的C#设计技巧
  • .net中调用windows performance记录性能信息
  • @Bean有哪些属性
  • [2019.3.5]BZOJ1934 [Shoi2007]Vote 善意的投票
  • [AHOI2009]中国象棋 DP,递推,组合数
  • [ANT] 项目中应用ANT
  • [Asp.net MVC]Asp.net MVC5系列——Razor语法
  • [AutoSar]状态管理(五)Dcm与BswM、EcuM的复位实现
  • [bzoj2957]楼房重建