将包含父子关系的扁平列表 List<Demo> 转换成树形结构的 List<DemoVO>,每个节点包含自己的子节点列表

1.stream递归操作

复制代码
    private List<DemoVO> createtree(List<Demo> datas) {
        //得到父节点
        return datas.stream()
                .filter(m -> TargetConstants.ROOT.equalsIgnoreCase(m.getParentId()))
                .map(m -> {
                    DemoVO vo = new DemoVO();
                    vo.setTaxonomyId(m.getPlatformTaxonomyId());
                    vo.setTaxonomyName(m.getPlatformTaxonomyName());
                    vo.setType(m.getType());
                    vo.setStatus(m.getStatus());
                    vo.setUpdateTime(m.getUpdateTime());
                    vo.setChildren(buildChildNodes(m, datas));
                    return vo;
                })
                .collect(Collectors.toList());
    }

    private List<DemoVO> buildChildNodes(Demo root, List<Demo> list){
        return list.stream()
                .filter(m -> Objects.equals(root.getPlatformTaxonomyId(), m.getParentId()))
                .map(m -> {
                    DemoVO vo = new DemoVO();
                    vo.setTaxonomyId(m.getPlatformTaxonomyId());
                    vo.setTaxonomyName(m.getPlatformTaxonomyName());
                    vo.setType(m.getType());
                    vo.setStatus(m.getStatus());
                    vo.setUpdateTime(m.getUpdateTime());
                    vo.setChildren(buildChildNodes(m, list));
                    return vo;
                }).collect(Collectors.toList());
    }

关键点

  1. 递归算法:

    • 通过 buildChildNodes 方法递归构建子树,直到没有子节点为止。
  2. 数据关联:

    • 通过 parentId 和 platformTaxonomyId 的匹配建立父子关系。
  3. 不变性:

    • 假设 Demo是只读的,每次递归创建新的 DemoVO 对象。

2.使用栈或队列的迭代方式可避免递归深度问题(适合超深层级数据):

复制代码
private List<DemoVO> createTreeIterative(List<Demo> datas) {
    Map<String, DemoVO> nodeMap = new HashMap<>();
    Map<String, List<Demo>> parentToChildren = datas.stream()
            .collect(Collectors.groupingBy(Demo::getParentId));

    // 所有节点预创建
    datas.forEach(data -> {
        DemoVO vo = new DemoVO();
        vo.setTaxonomyId(data.getPlatformTaxonomyId());
        vo.setTaxonomyName(data.getPlatformTaxonomyName());
        nodeMap.put(data.getPlatformTaxonomyId(), vo);
    });

    // 构建父子关系
    nodeMap.values().forEach(vo -> {
        List<Demo> childrenData = parentToChildren.get(vo.getTaxonomyId());
        if (childrenData != null) {
            vo.setChildren(childrenData.stream()
                    .map(child -> nodeMap.get(child.getPlatformTaxonomyId()))
                    .collect(Collectors.toList()));
        }
    });

    // 返回根节点
    return parentToChildren.getOrDefault(TargetConstants.ROOT, Collections.emptyList())
            .stream()
            .map(root -> nodeMap.get(root.getPlatformTaxonomyId()))
            .collect(Collectors.toList());
}
相关推荐
NendoZen几秒前
mangopi(芒果派)MQ-R T113 Buildroot开启adbd调试
linux·嵌入式硬件
Huangjin007_9 分钟前
【Linux 系统篇(二十九)】文件(六):动静态库制作
linux·运维·服务器
额额额对了21 分钟前
Linux 驱动学习笔记(部分)
linux·笔记·学习
guo_wen_qiang26 分钟前
云服务器redis主从复制-哨兵模式
运维·服务器·redis
zhikouai29 分钟前
AI辅助逆向工程链路:从二进制接入到等价性校验
java·linux·前端
可信时间戳36 分钟前
原创作品如何做版权认证申请?先备材料,再挑路径
服务器·音视频·可信时间戳·权利卫士
北城笑笑37 分钟前
Server 18 ,Nginx 双服务器 HTTP转HTTPS 代理实战( HTTP 地址换 HTTPS 域名 )
运维·服务器·前端·后端·nginx·http·https
程序员-Benothing39 分钟前
Linux磁盘IO性能分析:iostat、iotop、fio实战
linux·运维·服务器
I'mChloe1 小时前
不再逐台装Docker:我用Ansible Playbook批量统一服务器环境
服务器·docker·ansible
LiaoWL1231 小时前
从零开始学 Linux(一):目录结构、常用命令与 VIM 编辑器上手
linux·运维·服务器