【问题标题】:Why is the recursive insertion method of the BST not working为什么BST的递归插入方法不起作用
【发布时间】:2015-11-08 17:44:43
【问题描述】:

我编写了以下代码来实现 BST 的递归插入方法。但是,当我按顺序打印树时,它会在插入之前打印原始树。似乎没有插入该元素。请帮帮我。提前致谢。还请建议更改代码。顺便说一句,遍历顺序中的初始树是 2 5 5 6 7 8。

package DataStructures;

class TreeNode {
    private TreeNode parent;
    private TreeNode childLeft;
    private TreeNode childRight;
    private int key;

    public TreeNode(){

    }

    public TreeNode(int key) {
        this(key, null);
    }

    public TreeNode(int key, TreeNode parent) {
        this(key, parent, null, null);
    }

    public TreeNode(int key, TreeNode parent, TreeNode childLeft, TreeNode childRight) {
        this.key = key;
        this.parent = parent;
        this.childLeft = childLeft;
        this.childRight = childRight;
    }

    public int getKey() {
        return key;
    }

    public void setKey(int key) {
        this.key = key;
    }

    public TreeNode getParent() {
        return parent;
    }

    public void setParent(TreeNode parent) {
        this.parent = parent;
    }

    public TreeNode getChildLeft() {
        return childLeft;
    }

    public void setChildLeft(TreeNode childLeft) {
        this.childLeft = childLeft;
    }

    public TreeNode getChildRight() {
        return childRight;
    }

    public void setChildRight(TreeNode childRight) {
        this.childRight = childRight;
    }
}

public class BinarySearchTreeBasicTest {
    private static class BinarySearchTree {
        private TreeNode root;
        private TreeNode maxNode = new TreeNode(0);

        public BinarySearchTree(TreeNode root) {
            this.root = root;
        }

        public void printTheTreeInOrderWalk(TreeNode x) {
            if (x != null) {
                printTheTreeInOrderWalk(x.getChildLeft());
                System.out.print(x.getKey() + " ");
                printTheTreeInOrderWalk(x.getChildRight());
            }
        }









        public void insertNode(TreeNode node, int key){
            if (node == null){
                node = new TreeNode(key);
            }
            else{
                if (node.getKey() > key){
                    insertNode(node.getChildLeft(), key);
                } else if (node.getKey() < key){
                    System.out.println("k");
                    insertNode(node.getChildRight(), key);
                } else{
                    // dont do anything
                }
            }
        }
    }

    public static void main(String[] args) {
        TreeNode rootNode = new TreeNode(6);
        BinarySearchTree tree = new BinarySearchTree(rootNode);
        TreeNode node1 = new TreeNode(5);
        TreeNode node2 = new TreeNode(7);
        rootNode.setChildLeft(node1);
        rootNode.setChildRight(node2);
        node1.setParent(rootNode);
        node2.setParent(rootNode);
        TreeNode node3 = new TreeNode(2);
        TreeNode node4 = new TreeNode(5);
        node1.setChildLeft(node3);
        node1.setChildRight(node4);
        node3.setParent(node1);
        node4.setParent(node1);
        TreeNode node5 = new TreeNode(8);
        node5.setParent(node2);
        node2.setChildRight(node5);
        tree.insertNode(rootNode, 3);
        tree.printTheTreeInOrderWalk(rootNode);
    }
}

【问题讨论】:

    标签: java recursion data-structures insert binary-search-tree


    【解决方案1】:

    在 Java 中,参数是按值传递的。在insertNode 中,如果您不对node 做任何其他事情,那么node = new TreeNode(key); 行将不会做任何有用的事情。

    在树中插入的典型实现是通过返回将替换前一个的TreeNode

    private TreeNode insertNode(TreeNode node, int key){
        if (node == null){
            node = new TreeNode(key);
        }
        else{
            if (node.getKey() > key){
                node.setChildLeft(insertNode(node.getChildLeft(), key));
            } else if (node.getKey() < key){
                node.setChildRight(insertNode(node.getChildRight(), key));
            } else{
                // dont do anything
            }
        }
        return node;
    }
    

    再进一步,前面的方法实际上应该是privatepublic 方法应如下所示:

    public void insertNode(int key){
        root = insertNode(root, key);
    }
    

    【讨论】:

    • 在 java 中,参数是通过引用而不是值传递的......但是我在我的代码中发现了错误。在第一个 if 语句中,传递了对 null 的引用,因此如果将它分配给某个对象,它实际上不会更改分配引用最初引用的对象。
    • @coder12345 您的措辞很难理解,但我认为您实际上是在描述 按值传递 是什么。在 Java 中,这就是真正传递参数的方式:按值
    【解决方案2】:

    在您的insertNode() 方法中,您只是在创建一个新节点;您永远不会将新创建的节点添加到其父节点。您应该检查是否要在此处插入,或者您应该返回新返回的节点并进行相应的设置。

    如果您不希望与当前程序有太多偏差,可以进行以下更改。

    public void insertNode(TreeNode node, int key) {     
       if (node.getKey() > key) {
           if (node.left == null) { //check if you want to insert the node here
               TreeNode newNode = new TreeNode(key);
               node.left = newNode;
           } else {
                insertNode(node.getChildLeft(), key);
           }
       } else if (node.getKey() < key) {
           if(node.right == null){ //check if you want to insert the node here
                TreeNode newNode = new TreeNode(key);
                node.right = newNode;    
            } else {
                 insertNode(node.getChildRight(), key);
            }
       } else {
             // don't do anything
       }
    }
    

    【讨论】:

      猜你喜欢
      • 2022-11-12
      • 2018-03-25
      • 1970-01-01
      • 2021-01-31
      • 1970-01-01
      • 2023-03-17
      • 1970-01-01
      • 2019-08-03
      • 2014-04-24
      相关资源
      最近更新 更多