Stream流分组

一、准备4个用户对象

User user1 = User.builder()
                .name("blues")
                .sex("man")
                .age(20)
                .build();
        User user2 = User.builder()
                .name("blues")
                .sex("woman")
                .age(19)
                .build();
        User user3 = User.builder()
                .name("blues")
                .sex("woman")
                .age(18)
                .build();
        User user4 = User.builder()
                .name("blues")
                .sex("woman")
                .age(17)
                .build();
        List<User> users = new ArrayList<>();
        users.add(user3);
        users.add(user2);
        users.add(user3);
        users.add(user4);

 二、按属性给对象分组

例子:按性别给用户分组

        Map<String, List<User>> sexAndUserMap = users.parallelStream()
                .collect(Collectors.groupingBy(User::getSex));

三、按A属性分组统计B属性List(Set)

按性别分组统计名称List

Map<String, List<String>> sexAndNameListMap = users.parallelStream()
                .collect(Collectors.groupingBy(User::getSex, Collectors.mapping(User::getName, Collectors.toList())));

按性别分组统计名称Set

Map<String, Set<String>> sexAndNameSetMap = users.parallelStream()
                .collect(Collectors.groupingBy(User::getSex, Collectors.mapping(User::getName, Collectors.toSet())));

四、按A属性分组统计B属性和对象本身

按性别分组统计名称以及用户本身。

Map<String, Map<String, User>> sexAndNameAndDataMap = users.parallelStream()
                .collect(Collectors.groupingBy(User::getSex, Collectors.toMap(User::getName, data -> data)));

这里需要确保B属性在A属性下是唯一的,

示例中得保证名称在各性别组下是唯一的否则会产生用户覆盖。如果不是唯一的,可以采用多级分组

五、多级分组,按A属性分组,在此基础上按B属性分组

Map<String, Map<String, List<User>>> SexAndNameAndUserListMap = users.parallelStream()
                .collect(Collectors.groupingBy(User::getSex, Collectors.groupingBy(User::getName)));

六、遍历对象拿A和B属性建立Map映射关系

遍历用户,构建一个名称与性别的Map映射关系

Map<String, String> nameAndSexMap = users.parallelStream()
                .collect(Collectors.toMap(User::getName, User::getSex));

这里需要确保A在全局下是唯一的,否则会出现B属性值覆盖的情况

在示例中需要确保名称在所有用户下是唯一的,否则会出现性别覆盖的情况

Java 8 及更高版本中引入了 Stream API,它提供了一种声明式的方式对集合数据进行各种高效的操作。Stream 流操作支持诸如过滤、映射、收集等常见模式。而“流分组”通常是指通过 `Collectors.groupingBy` 方法将元素按照某种规则分类并汇总。 ### 分组基本概念 当你希望依据某些条件对一组对象进行归类时,就可以利用 `groupingBy` 收集器来实现这一需求。例如统计每个部门有多少员工或是按字母顺序整理单词列表等等场景都非常适合采用这种方式来进行处理。 ### 简单示例 假设我们有一个包含若干雇员信息的 Employee 类型 List 集合: ```java class Employee { private String name; private int departmentId; // 构造函数、getter 和 setter 略... } List<Employee> employeeList = Arrays.asList( new Employee("Alice", 1), new Employee("Bob", 2), new Employee("Charlie", 1) ); ``` 接下来我们将根据所属部门 ID 对职员们加以区分,并得到一个 Map<Integer, List<String>> 形式的最终结果表示各别部们的成员姓名清单。 ```java Map<Integer, List<String>> groupedByName = employeeList.stream() .collect(Collectors.groupingBy(Employee::getDepartmentId, Collectors.mapping(Employee::getName, Collectors.toList()))); System.out.println(groupedByName); // 输出类似于 {1=[Alice, Charlie], 2=[Bob]} ``` 上述代码片段展示了如何基于部门编号进行简单地分区动作;同时我们也学习到了另一个有用的辅助工具 - mapping(),它允许自定义转换逻辑生成新的键值关联形式而非单纯保留原始实体本身作为 value 组件的一部分参与构建整体 map 数据结构。 --- 当然还可以更进一步复杂化我们的查询请求,比如计算出各个小组内的平均年龄之类的额外指标出来,这时候就需要借助二次聚合功能的支持啦!
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值