亦有人 发表于 2023-3-11 16:30:00

java删除二叉树节点的实现

想求懂java的大哥指导为什我写的del方法无法删除节点
BinaryTree类创建二叉树:

public class BinaryTree {


    private Hero root;
    Scanner myScanner =new Scanner(System.in);

    public Hero createBinary() {

      Hero hero = null;

      System.out.println("你是否需要创造新节点y/n");
      String key = myScanner.next();
      if ("y".equals(key)) {
            System.out.print("请输入 id = ");
            int id = myScanner.nextInt();
            System.out.print("请输入 name = ");
            String name = myScanner.next();
            hero = new Hero(id, name);
      } else if ("n".equals(key)) {
//            hero = null;
            return null;
      }

      hero.setLeftChild(createBinary());
      hero.setRightChild(createBinary());
      return hero;
      }



//      Hero p = root;
//      if (p == null) {
//            root = hero;
//            return;
//      } else {
//            if (p.getLeftChild() == null) {
//                p.setLeftChild(hero);
//                p = p.getLeftChild();
//            } else if (p.getRightChild() == null) {
//                p.setRightChild(root);
//                p = p.getRightChild();
//            }
//      }


    public Hero getRoot() {
      return root;
    }

    public void setRoot(Hero root) {
      this.root = root;
    }

}



Hero是节点类

public class Hero {
    private Hero leftChild;
    private Hero rightChild;
    private int id;
    private String name;
    private int tag = 0;//0为未遍历,1为已遍历

    public int getTag() {
      return tag;
    }

    public void setTag(int tag) {
      this.tag = tag;
    }

    public Hero(int id, String name) {
      this.id = id;
      this.name = name;
    }

    public Hero getLeftChild() {
      return leftChild;
    }

    public void setLeftChild(Hero leftChild) {
      this.leftChild = leftChild;
    }

    public Hero getRightChild() {
      return rightChild;
    }

    public void setRightChild(Hero rightChild) {
      this.rightChild = rightChild;
    }

    public int getId() {
      return id;
    }

    public void setId(int id) {
      this.id = id;
    }

    public String getName() {
      return name;
    }

    public void setName(String name) {
      this.name = name;
    }


    @Override
    public String toString() {
      return "Hero{" +
                "id=" + id +
                ", name='" + name + '\'' +
                '}';
    }

}


DeleteTree是实现删除节点的类
public class DeleteTree {

    private static Scanner myScanner = new Scanner(System.in);
    public static void del(Hero tree, int id) {
      Stack<Hero> stack = new Stack<>();

      Hero p = tree;
      if (p == null) {
            System.out.println("该二叉树为空...");
            return;
      } else {
            while (p != null) {
                if (p.getId() == id) {
                  p = null;
                }
                else {
                  if (p.getRightChild() != null) {
                        stack.push(p.getRightChild());
                  }
                  if (p.getLeftChild() != null) {
                        p = p.getLeftChild();
                  } else if (!stack.empty()) {
                        p = stack.pop();
                  } else {
                        break;
                  }
                }
            }
      }
    }

}


TraMain是实现main方法的类
public class TraMain {

    static Scanner myScanner = new Scanner(System.in);

    public static void main(String[] args) {

      TraMain traMain = new TraMain();
      BinaryTree binaryTree = new BinaryTree();
      Hero BinaryTree = binaryTree.createBinary();//这样子一颗二叉树就搞好了
      System.out.println("===============递归前序遍历===============");
      traMain.preTravers(BinaryTree);//前序遍历

      DeleteTree.del(BinaryTree, 2);

      System.out.println("===============递归前序遍历===============");
      traMain.preTravers(BinaryTree);//前序遍历
      /**
      System.out.println("===============递归中序遍历===============");
      traMain.inorderTra(BinaryTree);
      System.out.println("===============递归后序遍历===============");
      traMain.postTra(BinaryTree);
      System.out.println("===============非递归前序遍历===============");
      traMain.nonRePreTra(BinaryTree);
      System.out.println("===== 中序非递归遍历(order) / 后序非递归遍历(post) =====");
      System.out.print("请输入 order 或 post: ");
      String key = myScanner.next();
      if ("order".equals(key)) {
            System.out.println("===============非递归中序遍历===============");
            traMain.nonReorderTra(BinaryTree);
      } else {
            System.out.println("===============非递归后序遍历===============");
            traMain.nonRepostTra(BinaryTree);
      }
**/
    }

    //前序遍历二叉树的方法
    public void preTravers(Hero tree) {
      Hero p = tree;

      if (p == null) {
            return;
      }

      System.out.println(p);

      preTravers(p.getLeftChild());
      preTravers(p.getRightChild());
    }

    public void inorderTra(Hero tree) {
      Hero p = tree;

      if (p == null) {
            return;
      }

      inorderTra(p.getLeftChild());
      System.out.println(p);
      inorderTra(p.getRightChild());

    }

    public void postTra(Hero tree) {
      Hero p = tree;

      if (p == null) {
            return;
      }

      postTra(p.getLeftChild());
      postTra(p.getRightChild());
      System.out.println(p);
    }

    public void nonRePreTra(Hero tree) {
      Stack<Hero> stack = new Stack<Hero>();
      Hero p = tree;

      if (p == null) {
            return;
      }

      while (p != null) {

            if (p.getRightChild() != null) {
                stack.push(p.getRightChild());
            }
            System.out.println(p);
            if (p.getLeftChild() != null) {
                p = p.getLeftChild();
            } else if (stack.size() > 0) {
                p = stack.pop();
            } else {
                  p = null;
            }

      }
    }

    public void nonReorderTra(Hero tree) {
      Stack<Hero> stack = new Stack<Hero>();
      Hero p = tree;

      if (p == null) {
            return;
      }

      while (p != null) {
            while (p.getLeftChild() != null && p.getLeftChild().getTag() == 0) {
                stack.push(p);
                p = p.getLeftChild();
            }
            System.out.println(p);
            p.setTag(1);
            if (p.getRightChild() != null) {
                p = p.getRightChild();
            } else if (stack.size() != 0){
                p = stack.pop();
            } else {
                p = null;
            }
      }
    }

    public void nonRepostTra(Hero tree) {
      Stack<Hero> stack = new Stack<Hero>();
      Hero p = tree;

      if (p == null) {
            return;
      }
      while (p != null) {
            while (p.getLeftChild() != null && p.getLeftChild().getTag() == 0) {
                stack.push(p);
                p = p.getLeftChild();
            }
            if (p.getRightChild()!= null && p.getRightChild().getTag() == 0) {
                stack.push(p);
                p = p.getRightChild();
            } else {
                System.out.println(p);
                p.setTag(1);
                if (stack.size() != 0) {
                  p = stack.pop();
                } else if (stack.size() == 0) {
                  p = null;
                }
            }
      }
    }

}

sfqxx 发表于 2023-4-17 18:08:32

很高兴能够帮助您。按照您所提供的代码,我看不到有实现删除节点的代码行或方法调用。您可能需要添加以下代码:

public void delNode(Hero root, int id) {
    if (root == null) {
      return;
    }
    if(root.getId() == id){
      root = null;
    }else{
      delNode(root.getLeftChild(),id);
      delNode(root.getRightChild(),id);
    }
}

以上方法将递归遍历二叉树,搜索要删除的节点,并将其设置为NULL。

此外,在以下代码中:


DeleteTree.del(BinaryTree, 2);


应该让您想删除哪个节点作为“2”。这是一个静态调用,因此如果无法直接修复,则可能会出现nullPointerException。

最后,建议您在指向对象之前检查它是否为零。这样做可以避免NullPointerException异常。

我希望这可以解决您的问题!
有用请设置最佳答案
页: [1]
查看完整版本: java删除二叉树节点的实现