Java 中的树实现(根、父级和子级)

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/19330731/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-12 16:10:36  来源:igfitidea点击:

Tree implementation in Java (root, parents and children)

javatreestructure

提问by Carlos

I need to create a tree structure similar as the attached image in Java. I've found some questions related to this one but I haven't found a convincing and well explained response. The application business consists in food super categories (main courses, desserts and other). Each of these categories can have parent items or children items and so on.

我需要创建一个类似于 Java 中附加图像的树结构。我发现了一些与此相关的问题,但没有找到令人信服且解释清楚的答复。应用业务包括食品超级品类(主菜、甜点等)。这些类别中的每一个都可以有父项或子项等。

Desired tree Structure

Desired tree Structure

采纳答案by Jonathan

import java.util.ArrayList;
import java.util.List;

public class Node<T> {
    private List<Node<T>> children = new ArrayList<Node<T>>();
    private Node<T> parent = null;
    private T data = null;

    public Node(T data) {
        this.data = data;
    }

    public Node(T data, Node<T> parent) {
        this.data = data;
        this.parent = parent;
    }

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

    public void setParent(Node<T> parent) {
        parent.addChild(this);
        this.parent = parent;
    }

    public void addChild(T data) {
        Node<T> child = new Node<T>(data);
        child.setParent(this);
        this.children.add(child);
    }

    public void addChild(Node<T> child) {
        child.setParent(this);
        this.children.add(child);
    }

    public T getData() {
        return this.data;
    }

    public void setData(T data) {
        this.data = data;
    }

    public boolean isRoot() {
        return (this.parent == null);
    }

    public boolean isLeaf() {
        return this.children.size == 0;
    }

    public void removeParent() {
        this.parent = null;
    }
}

Example:

例子:

import java.util.List;

Node<String> parentNode = new Node<String>("Parent"); 
Node<String> childNode1 = new Node<String>("Child 1", parentNode);
Node<String> childNode2 = new Node<String>("Child 2");     

childNode2.setParent(parentNode); 

Node<String> grandchildNode = new Node<String>("Grandchild of parentNode. Child of childNode1", childNode1); 
List<Node<String>> childrenNodes = parentNode.getChildren();

回答by Stephen Hosea

The process of assembling tree nodes is similar to the process of assembling lists. We have a constructor for tree nodes that initializes the instance variables.

组装树节点的过程类似于组装列表的过程。我们有一个用于初始化实例变量的树节点的构造函数。

public Tree (Object cargo, Tree left, Tree right) { 
    this.cargo = cargo; 
    this.left = left; 
    this.right = right; 
} 

We allocate the child nodes first:

我们先分配子节点:

Tree left = new Tree (new Integer(2), null, null); 
Tree right = new Tree (new Integer(3), null, null); 

We can create the parent node and link it to the children at the same time:

我们可以创建父节点并同时将其链接到子节点:

Tree tree = new Tree (new Integer(1), left, right); 

回答by galovics

This tree is not a binary tree, so you need an array of the children elements, like List.

这棵树不是二叉树,因此您需要一个子元素数组,例如 List。

public Node(Object data, List<Node> children) {
    this.data = data;
    this.children = children;
}

Then create the instances.

然后创建实例。

回答by tognyx

In the accepted answer

在接受的答案中

public Node(T data, Node<T> parent) {
    this.data = data;
    this.parent = parent;
}

should be

应该

public Node(T data, Node<T> parent) {
    this.data = data;
    this.setParent(parent);
}

otherwise the parent does not have the child in its children list

否则父级在其子级列表中没有子级

回答by Esdras Lopez

Accepted answerthrows a java.lang.StackOverflowErrorwhen calling the setParentor addChildmethods.

java.lang.StackOverflowError调用setParentaddChild方法时,接受的答案会抛出 a 。

Here's a slightly simpler implementation without those bugs:

这是一个没有这些错误的稍微简单的实现:

public class MyTreeNode<T>{
    private T data = null;
    private List<MyTreeNode> children = new ArrayList<>();
    private MyTreeNode parent = null;

    public MyTreeNode(T data) {
        this.data = data;
    }

    public void addChild(MyTreeNode child) {
        child.setParent(this);
        this.children.add(child);
    }

    public void addChild(T data) {
        MyTreeNode<T> newChild = new MyTreeNode<>(data);
        this.addChild(newChild);
    }

    public void addChildren(List<MyTreeNode> children) {
        for(MyTreeNode t : children) {
            t.setParent(this);
        }
        this.children.addAll(children);
    }

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

    public T getData() {
        return data;
    }

    public void setData(T data) {
        this.data = data;
    }

    private void setParent(MyTreeNode parent) {
        this.parent = parent;
    }

    public MyTreeNode getParent() {
        return parent;
    }
}

Some examples:

一些例子:

MyTreeNode<String> root = new MyTreeNode<>("Root");

MyTreeNode<String> child1 = new MyTreeNode<>("Child1");
child1.addChild("Grandchild1");
child1.addChild("Grandchild2");

MyTreeNode<String> child2 = new MyTreeNode<>("Child2");
child2.addChild("Grandchild3");

root.addChild(child1);
root.addChild(child2);
root.addChild("Child3");

root.addChildren(Arrays.asList(
        new MyTreeNode<>("Child4"),
        new MyTreeNode<>("Child5"),
        new MyTreeNode<>("Child6")
));

for(MyTreeNode node : root.getChildren()) {
    System.out.println(node.getData());
}

回答by Irshad ck

Here is my implementation in java for your requirement. In the treeNode class i used generic arrayto store the tree data. we can also use arraylistor dynamic arrayto store the tree value.

这是我根据您的要求在 Java 中的实现。在 treeNode 类中,我使用通用数组来存储树数据。我们还可以使用arraylist动态数组来存储树值。

public class TreeNode<T> {
   private T value = null;
   private TreeNode[] childrens = new TreeNode[100];
   private int childCount = 0;

    TreeNode(T value) {
        this.value = value;
    }

    public TreeNode addChild(T value) {
        TreeNode newChild = new TreeNode(value, this);
        childrens[childCount++] = newChild;
        return newChild;
    }

    static void traverse(TreeNode obj) {
        if (obj != null) {
            for (int i = 0; i < obj.childCount; i++) {
                System.out.println(obj.childrens[i].value);
                traverse(obj.childrens[i]);
            }
        }
        return;
    }

    void printTree(TreeNode obj) {
        System.out.println(obj.value);
        traverse(obj);
    }
}

And the client class for the above implementation.

以及上述实现的客户端类。

public class Client {
    public static void main(String[] args) {
        TreeNode menu = new TreeNode("Menu");
        TreeNode item = menu.addChild("Starter");
            item = item.addChild("Veg");
                item.addChild("Paneer Tikka");
                item.addChild("Malai Paneer Tikka");
            item = item.addChild("Non-veg");
                item.addChild("Chicken Tikka");
                item.addChild("Malai Chicken Tikka");
        item = menu.addChild("Main Course");
            item = item.addChild("Veg");
                item.addChild("Mili Juli Sabzi");
                item.addChild("Aloo Shimla Mirch");
            item = item.addChild("Non-veg");
                item.addChild("Chicken Do Pyaaza");
                item.addChild("Chicken Chettinad");
        item = menu.addChild("Desserts");
                item = item.addChild("Cakes");
                        item.addChild("Black Forest");
                        item.addChild("Black Current");
                item = item.addChild("Ice Creams");
                        item.addChild("chocolate");
                        item.addChild("Vanilla");
        menu.printTree(menu);
    }
}

OUTPUT

输出

Menu                                                                     
Starter                                                                 
Veg                                                                
Paneer Tikka                                                        
Malai Paneer Tikka                                                    
Non-veg                                                              
Chicken Tikka                                                      
Malai Chicken Tikka                                                 
Main Course                                                      
Veg                                                             
Mili Juli Sabzi                                                   
Aloo Shimla Mirch                                                  
Non-veg                                                               
Chicken Do Pyaaza                                                   
Chicken Chettinad                                                    
Desserts                                                         
Cakes                                                            
Black Forest                                                     
Black Current                                                   
Ice Creams                                                      
chocolate                                                       
Vanilla           

回答by Jeevana

In answer,it creates circular dependency.This can be avoided by removing parent inside Child nodes. i.e,

作为回答,它创建了循环依赖。这可以通过删除子节点内的父节点来避免。IE,

public class MyTreeNode<T>{     


    private T data = null;
    private List<MyTreeNode> children = new ArrayList<>();


    public MyTreeNode(T data) {
        this.data = data;

    }

    public void addChild(MyTreeNode child) {
        this.children.add(child);
    }

    public void addChild(T data) {
        MyTreeNode<T> newChild = new MyTreeNode<>(data);
        children.add(newChild);
    }

    public void addChildren(List<MyTreeNode> children) {
        this.children.addAll(children);
    }

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

    public T getData() {
        return data;
    }

    public void setData(T data) {
        this.data = data;
    }


}

Using the same example specified above,the output will be like this:

使用上面指定的相同示例,输出将如下所示:

{ "data": "Root", "children": [ { "data": "Child1", "children": [ { "data": "Grandchild1", "children": [] }, { "data": "Grandchild2", "children": [] } ] }, { "data": "Child2", "children": [ { "data": "Grandchild3", "children": [] } ] }, { "data": "Child3", "children": [] }, { "data": "Child4", "children": [] }, { "data": "Child5", "children": [] }, { "data": "Child6", "children": [] } ] }

{ "data": "Root", "children": [ { "data": "Child1", "children": [ { "data": "Grandchild1", "children": [] }, { "data": "Grandchild2", "children": [] } ] }, { "data": "Child2", "children": [ { "data": "Grandchild3", "children": [] } ] }, { "data": ": "Child3", "children": [] }, { "data": "Child4", "children": [] }, { "data": "Child5", "children": [] }, { "data": "Child6", "children": [] } ] }