比起2节点二叉树的删除操作,3节点的删除更加舒服一点,减少了很多扯蛋蛋的操作,加一个parent的只不过添加了一点点空间而已。
package io.github.chenshun00.web.tree;/*** @author luobo.cs@raycloud.com* @since 2021/8/13 1:24 下午*/public class BinaryTree2 {public static void main(String[] args) {BinaryTree2 binaryTree = new BinaryTree2();binaryTree.insertNode(22);binaryTree.insertNode(1);binaryTree.insertNode(4);binaryTree.insertNode(3);binaryTree.insertNode(10);binaryTree.insertNode(9);binaryTree.insertNode(9);binaryTree.insertNode(8);binaryTree.insertNode(190);binaryTree.insertNode(11);binaryTree.insertNode(12);binaryTree.insertNode(13);binaryTree.insertNode(231);binaryTree.insertNode(22);binaryTree.traverse();System.out.println("删除节点:===>" + binaryTree.deleteNode(9));binaryTree.traverse();System.out.println("删除节点:===>" + binaryTree.deleteNode(13));binaryTree.traverse();System.out.println("删除节点:===>" + binaryTree.deleteNode(22));binaryTree.traverse();System.out.println("删除节点:===>" + binaryTree.deleteNode(22));binaryTree.traverse();}public Node root;public boolean deleteNode(Integer data) {if (root == null) {return false;}//找到当前节点final Node node = doFindNode(data);//找不到节点的情况if (node == null) {return false;}//如果节点是根节点if (node == root) {//如果根节点是叶子节点if (isLeaf(root)) {root = null;} else {replace(root);}return true;}//被移除的是叶子节点if (isLeaf(node)) {//找到叶子节点的parent节点,并且说明当前节点是左(left)子树还是右子树(right)final Node parent = node.parent;if (parent.leftChild == node) {parent.leftChild = null;} else {parent.rightChild = null;}} else {replace(node);}return true;}public Node findNode(Integer data) {return root == null ? null : doFindNode(data);}public void insertNode(Integer data) {if (root == null) {root = new Node(null, null, null, data);} else {handleData(root, data);}}public void traverse() {doTraverse(root);System.out.println();}//==============================删==================================private void replace(Node node) {//找到左子树中最大的节点 或者 是右子树中最小的节点final Node next = findNext(node);final Node parent = next.parent;if (parent.leftChild == next) {parent.leftChild = null;} else if (parent.rightChild == next) {parent.rightChild = null;}node.data = next.data;}private Node findNext(Node node) {if (node.leftChild != null) {return doFindMaxNode(node.leftChild);}return doFindMinNode(node.rightChild);}private Node doFindMaxNode(Node node) {if (node.rightChild == null) {return node;} else {return doFindMaxNode(node.rightChild);}}private Node doFindMinNode(Node node) {if (node.leftChild == null) {return node;} else {return doFindMinNode(node.leftChild);}}public boolean isLeaf(Node node) {return node.leftChild == null && node.rightChild == null;}//==============================查==================================private Node doFindNode(Integer data) {return data >= root.data ? findRight(root, data) : findLeft(root, data);}/*** 找到右** @param root 根* @param data 数据* @return {@link Node}*/private Node findRight(Node root, Integer data) {if (root == null) {return null;}if (root.data.equals(data)) {return root;}if (data >= root.data) {//右子树return findRight(root.rightChild, data);} else {//左子树return findLeft(root.leftChild, data);}}private Node findLeft(Node root, Integer data) {if (root == null) {return null;}if (root.data.equals(data)) {return root;}if (data >= root.data) {//右子树return findRight(root.rightChild, data);} else {//左子树return findLeft(root.leftChild, data);}}//==============================遍历==================================private void doTraverse(Node node) {if (node == null) {System.out.println("么数据");return;}if (node.leftChild != null) {doTraverse(node.leftChild);}System.out.print(node.data + "\t");if (node.rightChild != null) {doTraverse(node.rightChild);}}//=================插入数据=====================private void handleData(Node root, Integer data) {if (data >= root.data) {handleRight(root, root.rightChild, data);} else {handleLeft(root, root.leftChild, data);}}//处理右子树private void handleRight(Node root, Node right, Integer data) {if (right == null) {right = new Node(null, null, root, data);root.rightChild = right;} else {handleData(right, data);}}//处理左子树private void handleLeft(Node root, Node left, Integer data) {if (left == null) {left = new Node(null, null, root, data);root.leftChild = left;} else {handleData(left, data);}}public static class Node {public Node(Node leftChild, Node rightChild, Node parent, Integer data) {this.leftChild = leftChild;this.rightChild = rightChild;this.parent = parent;this.data = data;}public Node leftChild;public Node rightChild;public Node parent;public Integer data;}}
