前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Java树形结构转换的实现

Java树形结构转换的实现

原创
作者头像
丿风轻丶云淡
修改2021-08-24 15:50:21
2K0
修改2021-08-24 15:50:21
举报
文章被收录于专栏:Xcore
代码语言:java
复制
public class TreeUtil {
    private String idField = "id";
    private String parentIdField = "parent_id";
    private String childrenField = "children";
    private List<String> fields = null;

    /**
     * 默认参数实例化
     * @return this
     */
    public static TreeUtil getInstance() {
        return new TreeUtil();
    }

    /**
     * 自定义id属性实例化
     * @param idField id属性
     * @return this
     */
    public static TreeUtil getInstance(String idField) {
        var util = getInstance();
        util.idField = idField;
        return util;
    }

    /**
     * 自定义id和父id属性实例化
     * @param idField id属性
     * @param parentIdField 父id属性
     * @return this
     */
    public static TreeUtil getInstance(String idField, String parentIdField) {
        var util = getInstance(idField);
        util.parentIdField = parentIdField;
        return util;
    }

    /**
     * 自定义id、父id和属性实例化
     * @param idField id属性
     * @param parentIdField 父id属性
     * @param childrenField 子节点属性
     * @return this
     */
    public static TreeUtil getInstance(String idField, String parentIdField, String childrenField) {
        var util = getInstance(idField, parentIdField);
        util.childrenField = childrenField;
        return util;
    }

    /**
     * 设置返回字段(不设置默认返回所有)
     * @param fields 返回字段
     * @return this
     */
    public TreeUtil setFields(String... fields) {
        this.fields = Arrays.stream(fields).filter(p -> !StrUtil.isBlank(p)).collect(Collectors.toList());
        if (this.fields.size() > 0 && !this.fields.contains(idField)) {
            this.fields.add(0, idField);
        }
        return this;
    }

    /**
     * List数据转树结构
     * @param list 完整数据
     * @return
     */
    public List<Map<String, Object>> tree(List<Map<String, Object>> list) {
        return tree(list, null);
    }

    /**
     * 返回指定父节点的树结构
     * @param list 完整数据
     * @param parentId 父id
     * @return
     */
    public List<Map<String, Object>> tree(List<Map<String, Object>> list, Object parentId) {
        Stream<Map<String, Object>> children;
        if (parentId == null) {
            children = list.stream().filter(p -> p.get(parentIdField) == null);
        } else {
            children = list.stream().filter(p -> p.get(parentIdField) != null && p.get(parentIdField).equals(parentId));
        }
        return children.map(m -> {
            val map = new LinkedHashMap<String, Object>();
            if (fields != null) {
                fields.forEach(e -> map.put(e, m.get(e)));
            }
            var child = tree(list, m.get(idField));
            if (child.size() == 0) child = null;
            map.put(childrenField, child);
            return map;
        }).collect(Collectors.toList());
    }

    /**
     * 获取当前节点
     * @param id 节点id
     * @param list
     * @return
     */
    public Map<String, Object> getNode(Object id, List<Map<String, Object>> list) {
        val node = list.stream().filter(p -> p.get(idField).equals(id)).findFirst().orElse(null);
        if (node != null) {
            node.put(childrenField, tree(list, id));
        }
        return node;
    }

    /**
     * 获取指定id的所有子节点
     * @param id
     * @param list
     * @return
     */
    public List<Map<String, Object>> getAllChildren(Object id, List<Map<String, Object>> list) {
        val node = getNode(id, list);
        return getAllChildren(node);
    }

    private List<Map<String, Object>> getAllChildren(Map<String, Object> node) {
        val typeReference = new TypeReference<List<Map<String, Object>>>() {};
        var children = Convert.convert(typeReference, node.get(childrenField));
        if (children == null) children = new ArrayList<>();
        if (children.size() > 0) {
            for (val entity : children) {
                children.addAll(getAllChildren(entity));
            }
        }
        node.remove(childrenField);
        children.add(node);
        return children;
    }

    /**
     * 获取指定id的所有父节点
     * @param list
     * @param id
     * @return
     */
    public List<Map<String, Object>> getAllParent(List<Map<String, Object>> list, Object id) {
        var parents = new ArrayList<Map<String, Object>>();
        var parent = list.stream().filter(p -> p.get(idField).equals(id)).findFirst().orElse(null);
        while (parent != null) {
            parents.add(parent);
            val parentId = parent.get(parentIdField);
            if (parentId == null) {
                parent = null;
            } else {
                parent = list.stream().filter(p -> p.get(idField).equals(parentId)).findFirst().orElse(null);
            }
        }
        return parents;
    }
}

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档