
本文介绍两种高效合并具有相同 id 的 person 对象的方法:使用 hashmap 手动聚合,或借助 stream api 配合 groupingby 实现函数式合并,最终生成去重且位置信息聚合的唯一对象列表。
本文介绍两种高效合并具有相同 id 的 person 对象的方法:使用 hashmap 手动聚合,或借助 stream api 配合 groupingby 实现函数式合并,最终生成去重且位置信息聚合的唯一对象列表。
在实际开发中,我们常需对 List
✅ 方案一:使用 HashMap 手动聚合(推荐用于复杂逻辑或需复用中间状态)
该方法时间复杂度为 O(n),清晰可控,适合需要自定义合并策略(如 contract 值取最大/平均/首个)的场景:
Map<integer person> mergedMap = new HashMap();
for (Person person : list) {
int id = person.getId();
if (!mergedMap.containsKey(id)) {
// 首次遇到该 ID,深拷贝或新建 Person(避免引用污染)
mergedMap.put(id, new Person(
person.getId(),
person.getContract(), // 此处可改为 Math.max(existing.getContract(), person.getContract())
new ArrayList(person.getPositions())
));
} else {
Person existing = mergedMap.get(id);
existing.getPositions().addAll(person.getPositions());
// 注意:若 contract 需要合并(如求和),此处补充逻辑
}
}
List<person> mergedList = new ArrayList(mergedMap.values());</person></integer>
⚠️ 注意事项:
- 原始 Person 类中的 position 字段应为 List
(首字母大写更符合 Java 命名规范,建议修正类名 position → Position); - 若 Person 包含可变状态(如 contract),需明确业务规则(保留首个?取最大值?累加?),示例中默认保留第一个出现的 contract 值;
- 使用 new ArrayList(...) 避免后续操作影响原始对象。
✅ 方案二:使用 Stream + Collectors.groupingBy()(函数式、简洁)
适用于逻辑简单、强调代码可读性与不可变性的场景:
List<person> mergedList = list.stream()
.collect(Collectors.groupingBy(
Person::getId,
LinkedHashMap::new, // 保持插入顺序(可选)
Collectors.collectingAndThen(
Collectors.toList(),
group -> {
Person first = group.get(0);
List<position> allPositions = group.stream()
.flatMap(p -> p.getPositions().stream())
.collect(Collectors.toList());
return new Person(
first.getId(),
first.getContract(), // 同样可替换为 group.stream().mapToInt(Person::getContract).sum()
allPositions
);
}
)
))
.values()
.stream()
.collect(Collectors.toList());</position></person>
? 提示:groupingBy 返回 Map
>,配合 collectingAndThen 可在分组后立即对每个 List 执行自定义聚合逻辑,避免额外遍历。
sc-java-to-ts-interface下载将后端 Java 接口文档转换为前端 TypeScript 类型定义(interface / type)。输入:飞书文档、Spring Boot 接口文档、Swagger/OpenAPI、手写 API 文档等。输出:包含请求参数与响应结果的 .md 文件,含完整 JSDoc 注释。触发关键词:Java 转 TS、接口转换、生成前端类型、接口文档转 TypeScript、DTO/VO/BO 转 interface、后端文档转前端类型、生成接口类型、类型定义生成。
✅ 最终效果
无论采用哪种方案,输入:
Person p1 = new Person(1, 470, List.of(new Position(45, LocalDate.now()), new Position(42, LocalDate.now()))); Person p2 = new Person(1, 320, List.of(new Position(35, LocalDate.now()))); List<person> list = List.of(p1, p2);</person>
都将输出唯一一个 Person 对象:
Person{id=1, contract=470, positions=[Position{id=45,...}, Position{id=42,...}, Position{id=35,...}]}
✅ 总结:优先选用 方案一(HashMap) 以保障性能与可维护性;若项目已重度使用 Stream 且逻辑简单,方案二更具表达力。两者均避免了原始代码中“边遍历边修改”及“未去重”的根本缺陷。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











