You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

JDK8+环境下合并列表中id与name相同的A类对象并聚合B列表

实现方案

推荐方案:Stream流分组合并(无需修改原类、无需反射)

直接用JDK自带的Stream分组能力实现,仅需几行代码就能满足需求,完全适配你无法修改A、B类的限制:

import org.junit.Test;
import java.util.AbstractMap;
import java.util.List;
import java.util.stream.Collectors;

public class MergeTest {
    @Test
    public void test() {
        List<A> originList = List.of(
                new A(1, "a1", List.of(new B(1, "1b"))),
                new A(1, "a1", List.of(new B(2, "2b"))),
                new A(2, "a2", List.of(new B(3, "3b")))
        );

        List<A> mergedList = originList.stream()
                // 以id+name作为分组键
                .collect(Collectors.groupingBy(a -> new AbstractMap.SimpleEntry<>(a.id, a.name)))
                .values()
                .stream()
                .map(sameGroup -> {
                    // 聚合同组所有B对象
                    List<B> mergedB = sameGroup.stream()
                            .map(a -> a.listB)
                            .flatMap(List::stream)
                            .collect(Collectors.toList());
                    // 构造合并后的A对象
                    A first = sameGroup.get(0);
                    return new A(first.id, first.name, mergedB);
                })
                .collect(Collectors.toList());
    }
}

// 原类定义无需任何修改
class A {
    public A(int id, String name, List<B> listB) {
        this.id = id;
        this.name = name;
        this.listB = listB;
    }
    int id;
    String name;
    List<B> listB;
}

class B {
    public B(int id, String name) {
        this.id = id;
        this.name = name;
    }
    int id;
    String name;
}

反射不适合该场景的原因

完全没必要用反射,理由如下:

  • 性能损耗:反射是运行时动态解析属性,性能远低于直接调用类的属性和构造方法
  • 维护成本高:反射代码可读性差,且如果自动生成的A、B类后续修改了属性名,编译期不会报错,只会在运行时抛出异常,排查成本极高
  • 需求匹配度低:当前场景分组键仅2个属性,合并逻辑简单,Stream实现的代码量比反射实现更少,更易维护

内容的提问来源于stack exchange,提问作者UnnameDSoS

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.02 19:27:03