二叉查找樹

package cc.stack.application;

class Node {
    int val;
    Node lchild;
    Node rchild;
    public Node(int var) {
        this.val = var;
    }
}

public class Main1 {

    /*
     * 若二叉樹是空樹,則查找失敗
     * 若x等於根結點的數據,則查找成功
     * 若x小於根結點的數據,則遞歸查找其左子樹,否則遞歸查找其右子樹
     */
    public static boolean contains(Node head, int number) {
        if(head == null)
            return false;
        if(head.val > number)
            return contains(head.lchild, number);
        else if(head.val < number)
            return contains(head.rchild, number);
        else 
            return true;
    }

    public static int findMin(Node head) {  //查找最小值
        if(head == null)
            return -1;
        if(head.lchild == null)
            return head.val;
        return findMin(head.lchild);

    }

    public static int findMax(Node head) {   //查找最大值
        if(head == null)
            return -1;
        if(head.rchild == null)
            return head.val;
        return findMax(head.rchild);

    }

    public static Node insert(Node head, int number) throws Exception {
        if(head == null) {
            Node insert_node = new Node(number);   //新建一個結點
            return insert_node;
        } 
        if(number > head.val) 
            head.rchild = insert(head.rchild, number);
        else if(number < head.val)
            head.lchild = insert(head.lchild, number);
        else
            throw new Exception("equal number");
        return head;

    }

    /*
     * 刪除結點分三種方式刪除結點
     *  1、刪除沒有子結點的結點,直接讓該結點的父結點的左結點或右結點指向空
     *  2、刪除有一個子結點的結點,直接讓該結點的父結點指向被刪除結點的剩餘結點 
     *  3、刪除有兩個子結點的結點,以被刪除結點的右結點的最左結點爲後繼結點, 用該結點替代要刪除的結點
     */ 
    public static boolean delete(Node head, int key) {  //刪除結點

        /*
         * 第一步:找到要刪除的結點以及它的父結點
         */
        Node parent = head; //保存要查找結點的父結點
        Node current = head; //保存查找到的結點
        if(head == null)
            return false;
        while(current != null && current.val != key) {
            parent = current;   //保存父結點
            if(key > current.val)
                current = current.rchild;
            else if(key < current.val)
                current = current.lchild;
        }
        if(current == null)
            return false;

        /*
         * 第二步:根據刪除結點的3種類型做相應處理
         */

        if(current.lchild == null && current.rchild == null) { //要刪除的結點沒有子結點
            if(head == current)  //如果要刪除的是根結點
                head = null;
            if(current == parent.lchild)  //如果要刪除的是左結點
                parent.lchild = null;
            else                          //如果要刪除的是右結點
                parent.rchild = null;
        } 
        else if(current.rchild == null) {                       //要刪除的結點只有左結點
            if(head == current)  //如果要刪除的是根結點
                head = null;
            if(current == parent.lchild)  //如果要刪除的是左結點
                parent.rchild = current.lchild;
            else                          //如果要刪除的是右結點
                parent.lchild = current.lchild;
        }
        else if(current.lchild == null) {                       //要刪除的結點只有右結點
            if(head == current)  //如果要刪除的是根結點
                head = null;
            if(current == parent.lchild)  //如果要刪除的是左結點
                parent.lchild = current.rchild;
            else                          //如果要刪除的是右結點
                parent.rchild = current.rchild;
        }
        else {                                                   //要刪除的結點有兩個結點
            /*
             * 第三步:去查找替代要被刪除結點的結點successor,刪除該結點,把值替換過去
             * */
            Node successor = current.rchild;
            Node successor_parent = current;
            while(successor != null && successor.lchild != null) {
                successor_parent = successor;
                successor = successor.lchild;
            }
            current.val = successor.val;
            successor_parent.lchild = null; 
        }
        return true;


    }

    public static void main(String[] args) throws Exception {
        Node node1 = new Node(8);
        Node node2 = new Node(3);
        Node node3 = new Node(10);
        Node node4 = new Node(1);
        Node node5 = new Node(6);
        Node node6 = new Node(14);
        Node node7 = new Node(4);
        Node node8 = new Node(7);
        Node node9 = new Node(13);
        node1.lchild = node2; node1.rchild = node3;
        node2.lchild = node4; node2.rchild = node5;
        node3.lchild = null; node3.rchild = node6; 
        node5.lchild = node7; node5.rchild = node8;
        node6.lchild = node9; node6.rchild = null;
        node4.lchild = null; node4.rchild = null;
        node7.lchild = null; node7.rchild = null;
        node8.lchild = null; node8.rchild = null;
        node9.lchild = null; node9.rchild = null;

        //System.out.println(contains(node1, 2));
       /* System.out.println(findMin(node1));
        System.out.println(findMax(node1));*/
        System.out.println(delete(node1, 3));
        //System.out.println(insert(node1, 2).lchild.lchild.rchild.val);
        System.out.println(node1.lchild.val);
    }
}
發佈了227 篇原創文章 · 獲贊 24 · 訪問量 32萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章