Java_解析字符串为树结构目录

数据示例:
system/test
system/admin
user/wxl/admin
user/wxl/trst
user/admin/wxl
admin/fundate

结果图片示例:
在这里插入图片描述

		//巧妙使用set集合去重,我之前使用的是递归

		//从数据库获取String集合
   		List<String> dbAllDirectory = mapper.getAllDirectory();
        Set<String> allDirectory = new HashSet<>();
        //将所有数据添加至set中(此处作为最后级目录)
        allDirectory.addAll(dbAllDirectory);
        //解析dbAllDirectory ,使用split截取数组,并放入allDirectory集合中(示例数据:user  ,  user/wxl  )
        //其实就是拆分一级目录,二级目录,三级目录...,最后级目录已在上面放入
        for (String directory : dbAllDirectory) {
            String[] split = directory.split("/");
            for (int i = 1; i < split.length; i++) {
                allDirectory.add(StringUtil.join("/", ArrayUtil.sub(split, 0, i)));
            }
        }
        //循环所有目录
        for (String directory : allDirectory) {
        	//目录中没有"/"分隔符,视为一级目录
            if (directory.indexOf("/") == -1) {
                TreeNodeModel treeNodeModel = new TreeNodeModel();
                treeNodeModel.setId(directory);
                treeNodeModel.setText(directory);
                treeNodeModel.setIconCls("colorHome-svg");
                result.addNode(treeNodeModel, null);
            } else {
                TreeNodeModel treeNodeModel = new TreeNodeModel();
                treeNodeModel.setId(directory);//当前目录及父目录为ID
                treeNodeModel.setText(directory.substring(directory.lastIndexOf("/") + 1));//截取当前目录名称
                treeNodeModel.setIconCls("colorFolder-svg");//放入放弃目录图标
                result.addNode(treeNodeModel, directory.substring(0, directory.lastIndexOf("/")));
            }
        }


//别人已经写好模型
package fd.tool.data;

import fd.exception.FdDebugException;
import fd.util.StringUtil;

import java.io.Serializable;
import java.util.*;

public class TreeModel implements Iterable<TreeNodeModel>, Serializable {

    private LinkedList<TreeNodeModel> list = new LinkedList<TreeNodeModel>();
    private Map<String, TreeNodeModel> nodeMap = new HashMap<String, TreeNodeModel>();
    private Map<String, TreeNodeModel> cache = new HashMap<String, TreeNodeModel>();
    private Map<String, String> c2p = new HashMap<String, String>();

    public TreeModel addNode(TreeNodeModel node, String parentId) {
        if (parentId != null && parentId.equals(node.getId())) {
            parentId = null;
        }
        if (c2p.containsKey(node.getId())) {
            String p = c2p.get(node.getId());
            if ((p != null && !p.equals(parentId)) || (parentId != null && !parentId.equals(p))) {
                throw new FdDebugException(node.getId() + "被两次加入本树.");
            }
        }
        c2p.put(node.getId(), parentId);

        if (nodeMap.containsKey(node.getId())) {
            return this;
        } else {
            nodeMap.put(node.getId(), node);
        }

        if (cache.containsKey(node.getId())) {
            node.setChildren(cache.get(node.getId()).getChildren());
            cache.remove(node.getId());//可以清除
        }

        if (StringUtil.isEmpty(parentId)) {
            list.add(node);
        } else {
            TreeNodeModel treeNodeModel = nodeMap.get(parentId);
            if (treeNodeModel == null) {
                if (cache.containsKey(parentId)) {
                    cache.get(parentId).addChild(node);
                } else {
                    TreeNodeModel p = new TreeNodeModel();
                    p.setId(parentId);
                    p.addChild(node);
                    cache.put(parentId, p);
                }
            } else {
                testAllParent(treeNodeModel, new HashSet<String>());
                treeNodeModel.addChild(node);
            }
        }
        return this;
    }

    public Iterator<TreeNodeModel> iterator() {

        for (String key : cache.keySet()) {
            list.add(cache.get(key));  //将孤儿作为根节点
        }

        cache.clear();
        return list.iterator();
    }

    public int maxLevel() {
        int m0 = 0;
        for (TreeNodeModel node : list) {
            int m = getMaxLevel(node, 1);
            m0 = Math.max(m0, m);
        }
        return m0;
    }

    private int getMaxLevel(TreeNodeModel node, int level) {
        int m0 = level;
        if (node.getChildren() == null || node.getChildren().size() == 0) {
            return level;
        } else {
            for (TreeNodeModel child : node.getChildren()) {
                int m = getMaxLevel(child, level + 1);
                m0 = Math.max(m0, m);
            }
            return m0;
        }
    }

    public void initLevel() {
        for (TreeNodeModel node : list) {
            initNodeLevel(node);
        }
    }

    private void initNodeLevel(TreeNodeModel node) {
        if (node.getChildren() == null || node.getChildren().size() == 0) {
            node.setLevel(1);
        } else {
            node.setLevel(2);
            for (TreeNodeModel child : node.getChildren()) {
                initNodeLevel(child);
                if (child.getLevel() >= node.getLevel()) {
                    node.setLevel(child.getLevel() + 1);
                }
            }
        }
    }

    /**
     * 从上层节点向下层节点进行父节点递归计算
     *
     * @param nodeOperator
     */
    public void callEachParent(TreeNodeOperator nodeOperator) {
        for (TreeNodeModel node : list) {
            callEachNode(node, nodeOperator, true);
        }
    }

    private void testAllParent(TreeNodeModel node, Set<String> outputSet) {
        if (node == null) {
            return;
        }
        String parentId = c2p.get(node.getId());
        if (parentId != null) {
            if (outputSet.add(parentId)) {
                testAllParent(nodeMap.get(parentId), outputSet);
            } else {
                throw new FdDebugException(node.getId() + "出现递归 current parentId:" + parentId);
            }
        }
    }

    /**
     * 从上层节点向下层节点进行父节点递归计算
     *
     * @param nodeOperator
     */
    public void callEachNode(TreeNodeOperator nodeOperator) {
        for (TreeNodeModel node : list) {
            callEachNode(node, nodeOperator, false);
        }
    }

    public void callEachNodeWithParentInfo(TreeNodeOperatorWithParentInfo operatorWithParentInfo) {
        for (TreeNodeModel node : list) {
            callEachNode(node, operatorWithParentInfo, false);
        }
    }

    private void callEachNode(TreeNodeModel node, TreeNodeOperatorWithParentInfo operatorWithParentInfo, boolean onlyParent) {
        if (node.getChildren() == null || node.getChildren().size() == 0) {
            // onlyParent时最下级节点,不做计算
            if (!onlyParent) {
                String partentId = c2p.get(node.getId());
                operatorWithParentInfo.execute(node, nodeMap.get(partentId));
            }
        } else {
            for (TreeNodeModel child : node.getChildren()) {
                callEachNode(child, operatorWithParentInfo, onlyParent);
            }
            // 确定先后顺序
            String partentId = c2p.get(node.getId());
            operatorWithParentInfo.execute(node, nodeMap.get(partentId));
        }

    }

    private void callEachNode(TreeNodeModel node, TreeNodeOperator nodeOperator, boolean onlyParent) {
        if (node.getChildren() == null || node.getChildren().size() == 0) {
            // onlyParent时最下级节点,不做计算
            if (!onlyParent) {
                nodeOperator.execute(node);
            }
        } else {
            for (TreeNodeModel child : node.getChildren()) {
                callEachNode(child, nodeOperator, onlyParent);
            }
            // 确定先后顺序
            nodeOperator.execute(node);
        }
    }

    public void removeNode(String nodeId) {
        for (int i = 0; i <= list.size(); i++) {
            removeNode(list.get(i), nodeId, list, i);
        }
    }

    private boolean removeNode(TreeNodeModel node, String nodeId, List<TreeNodeModel> nodes, int index) {
        if (node.getId().equals(nodeId)) {
            nodes.remove(index);
            return true;
        } else {
            List<TreeNodeModel> chidrens = node.getChildren();
            for (int i = 0; i <= chidrens.size(); i++) {
                removeNode(chidrens.get(i), nodeId, chidrens, i);
            }
        }
        return false;
    }
}
//别人已写好模型
package fd.tool.data;

import fd.util.StringUtil;
import lombok.Data;
import lombok.experimental.Accessors;

import java.util.LinkedList;
import java.util.List;

/**
 * 针对extjs设计的树节点模型
 */

@Data
@Accessors(chain = true)
public class TreeNodeModel {
    private String id;
    private String text;
    private boolean leaf = true;
    private String iconCls;
    private boolean expanded = false;
    private List<TreeNodeModel> children;
    private int level = 0;

    public List<TreeNodeModel> getChildren() {
        return children;
    }

    public void setChildren(List<TreeNodeModel> children) {
        this.children = children;
        if (children != null) {
            this.leaf = false;
        }
    }

    public TreeNodeModel addChild(TreeNodeModel node) {
        if (children == null) {
            this.children = new LinkedList<TreeNodeModel>();
            this.leaf = false;
        }
        children.add(node);
        return this;
    }


    public String getText() {
        return StringUtil.isBlank(text) ? "[" + id + "]" : text;
    }

}

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
AST(Abstract Syntax Tree,抽象语法树)是将代码解析为树状结构的一种数据结构,用于表示程序代码的语法结构。在Java中,可以使用第三方库解析动态字符串并生成语法树。 在Java中,常用的AST解析工具是Eclipse JDT(Java Development Tools)。JDT是Eclipse平台上的Java开发工具,它提供了解析Java代码并生成AST的能力。 使用JDT解析动态字符串并生成语法树的一般步骤如下: 1. 导入JDT相关的库,例如org.eclipse.jdt.core.dom。 2. 创建一个ASTParser对象,该对象将用于解析字符串并生成AST。 3. 调用setSource方法,将要解析字符串作为参数传入。 4. 调用createAST方法,该方法将返回一个CompilationUnit对象,表示生成的语法树。 5. 使用CompilationUnit对象进行进一步的操作,例如遍历、分析、修改等。 以下是一个简单示例: ```java import org.eclipse.jdt.core.dom.AST; import org.eclipse.jdt.core.dom.ASTParser; import org.eclipse.jdt.core.dom.CompilationUnit; public class ASTParserExample { public static void main(String[] args) { String code = "public class HelloWorld { public static void main(String[] args) { System.out.println(\"Hello, World!\"); } }"; ASTParser parser = ASTParser.newParser(AST.JLS11); parser.setSource(code.toCharArray()); CompilationUnit cu = (CompilationUnit) parser.createAST(null); // 进一步操作语法树,例如遍历、分析、修改等 // 输出语法树 System.out.println(cu.toString()); } } ``` 这段代码会将给定的动态字符串解析为一个表示整个Java程序语法结构的语法树,并输出语法树的字符串表示。 需要注意的是,AST解析是一个复杂的过程,涉及到语法分析和语义分析等步骤。随着程序代码的复杂度增加,可能需要进一步了解AST的使用和相关API,以便更好地处理和分析生成的语法树。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值