繁体   English   中英

如何在Java中创建动态树数据结构

[英]How to create dynamic tree data structure in Java

具体来说,我需要代表以下内容:

  1. 任何节点上的树都可以有任意数量的子代
  2. 每个父节点(在根之后)只是一个字符串(其子代也是字符串)
  3. 我需要能够获得父代,并列出代表给定节点的输入字符串,列出所有子代(某种形式的列表或字符串数​​组)
  4. 根据父级和子级之间的引用关系动态填充树结构。 给出的示例是我有一个member1赞助者另一个member2,而member2赞助者成员3等等。 已经有表记录关系

有没有可用的结构呢?

像图像中那样建造一棵树

我的数据来自数据库或列表,我将遍历具有名称和关系的信息,以确定该节点是根节点,父节点还是子节点。

因此,在循环中,我找到了一个孩子,我需要引用父对象,以便在将孩子添加到其父对象之前可以将其与父对象的关系进行比较。

我找到的最接近的代码。

public class TreeNode<T> implements Iterable<TreeNode<T>> {

    T data;
    TreeNode<T> parent;
    List<TreeNode<T>> children;

    public TreeNode(T data) {
        this.data = data;
        this.children = new LinkedList<TreeNode<T>>();
    }

    public TreeNode<T> addChild(T child) {
        TreeNode<T> childNode = new TreeNode<T>(child);
        childNode.parent = this;
        this.children.add(childNode);
        return childNode;
    }

    // other features ...

}
Sample usage:

TreeNode<String> root = new TreeNode<String>("root");
{
    TreeNode<String> node0 = root.addChild("node0");
    TreeNode<String> node1 = root.addChild("node1");
    TreeNode<String> node2 = root.addChild("node2");
    {
        TreeNode<String> node20 = node2.addChild(null);
        TreeNode<String> node21 = node2.addChild("node21");
        {
            TreeNode<String> node210 = node20.addChild("node210");
        }
    }
}

到目前为止,这是我所做的。 父项将被最新条目覆盖,因此我无法检索之前添加的内容。

public static TreeNode<String> getSet1() throws IOException {

        BufferedReader reader = new BufferedReader(new FileReader("test.txt"));
        String line;

        while ((line = reader.readLine()) != null) {
            String[] items = line.split(":");

            String name = items[0];
            String parent = items[1];
            String type = items[2];

            if (parent.equalsIgnoreCase("-") && type.equalsIgnoreCase("mainparent")) {

                root = new TreeNode<String>(name);


            } else if (type.equalsIgnoreCase("ChildParent")  && parent.equalsIgnoreCase(root.toString())) {

                childParent = root.addChild(name);

           } else if (type.equalsIgnoreCase("Child") && parent.equalsIgnoreCase(childParent.toString())) {

                child = childParent.addChild(name);
            }

        }

        return root;
    }

您的图表示一棵任意深度的树,但是您的代码仅处理祖父母->父->子关系(在根中有一个祖父母)。

我会忽略类型,因为您所需要的只是一个人的名字和他们父母的名字。 如果父名称是破折号,则说明您拥有根。

现在,对于每个人,您都需要在树中已有父节点(假设父节点在列表中的子节点之前-如果不是这样,问题将变得更加复杂,因为您将不得不暂时存储孤儿,每个新人都看他们是否是孤儿的父母)。

为了按名称获取父级,您应该将已经处理过的每个人存储在与树平行的第二个数据结构中。 第二个数据结构应使按名称查找某人变得容易。 地图,尤其是哈希表非常适合此操作。 它是这样工作的:

Map processedPersonsMap=new Hashtable<String, TreeNode<String>>();

对于每个人,您都将它们存储在地图中,并按其名称索引:

TreeNode<String> person=...;
processedPersonsMap.put(person.getData(), person);

当您读一个新的人并且他们父母的名字不是破折号时,您会查找父母:

String parentName=items[1];
TreeNode<String> parent=processedPersonsMap.get(parentName);

这样,无论树有多深,您总会找到合适的父母。 但是,请记住,这需要一个有效的输入文件,每个孩子都位于其父母之后,并且不包含循环引用或缺少父母。

如果不满足这些条件,则必须明确处理它们。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM