2008年2月28日

删除结点的时候考虑情况分三种 叶子节点 有一个子结点 有两个子节点
----
using System;
using System.Collections.Generic;
using System.Text;


namespace chapt10_01
{
    //线索二叉搜索树
    class Node
    {
        public Node lchild;
        public Node rchild;
        public int lthread=1;
        public int rthread=1;
        public int Value;
        public Node(int v) { Value = v; }
    }

    class ThreadBinarySearchTree : chapt10_01.IThreadBinarySearchTree
    {
        private Node head;
        //0thread 1node
        public ThreadBinarySearchTree()
        {
            head = new Node(0);
            head.lthread = 0;
            head.lchild = head;
        }

        public void find(int element, ref Node parent, ref Node currentNode)
        { }

        public void insert(int element) {

            Node newNode = new Node(element);
            Node currentNode,parent;
            //empty
            if (head.lthread == 0)
            {
                head.lthread = 1;
                head.lchild = newNode;
                newNode.lchild = head;
                newNode.rchild = head;
                newNode.lthread = 0;
                newNode.rthread = 0;
            }
            else
            {
                currentNode = head.lchild;
                parent = head;
                while (currentNode != null)
                {
                    parent = currentNode;

                    if (head.lchild == head)
                    {
                        parent = head;
                    }
                    else if (element == currentNode.Value)
                    {
                        Console.Write("{0} is exist.canot insert", element);
                        return;
                    }
                    else if (element < currentNode.Value && currentNode.lthread == 1)
                        currentNode = currentNode.lchild;
                    else if (element < currentNode.Value && currentNode.lthread == 0)
                        currentNode = null;
                    else if (element > currentNode.Value && currentNode.rthread == 1)
                        currentNode = currentNode.rchild;
                    else if (element > currentNode.Value && currentNode.rthread == 0)
                        currentNode = null;                   
                }
                newNode.lthread = 0;
                newNode.rthread = 0;
                if (parent == head)
                {
                    head.lthread = 1;
                    head.lchild = newNode;
                    newNode.lchild = head;
                    newNode.rchild = head;
                }
                else if (element < parent.Value)
                {
                    newNode.lchild = parent.lchild;
                    newNode.rchild = parent;
                    parent.lthread = 1;
                    parent.lchild = newNode;
                }
                else if (element > parent.Value)
                {
                    newNode.lchild = parent;
                    newNode.rchild = parent.rchild;
                    parent.rthread = 1;
                    parent.rchild = newNode;
                }
            }

        }

        //找到中序后继
        public Node Inorder_successor(ref Node currentNode)
        {
            //right is thred
            if (currentNode.rthread == 0)
            {
                currentNode = currentNode.rchild;
            }
            else
            {//有孩子的最左
                currentNode = currentNode.rchild;
                while (currentNode.lthread != 0)
                {
                    currentNode = currentNode.lchild;
                }
            }
            return currentNode;
        }
        //前驱
        public Node Inorder_per(ref Node currentNode)
        {
            //Node parent;
            //right is thred
            if (currentNode.lthread == 0)
            {
                currentNode = currentNode.lchild;
            }
            else
            {
                currentNode = currentNode.lchild;
                while (currentNode.rthread != 0)
                {
                    //parent = currentNode;
                    currentNode = currentNode.rchild;
                }
            }
            return currentNode;
        }
            

        public void Inorder_traversal()
        {
            if (head.lchild == head)
            {
                Console.WriteLine("Tree is empty");
                return;
            }
            Node currentNode;
            currentNode = head.lchild;
            while (currentNode.lthread == 1)
            {
                currentNode = currentNode.lchild;
            }
            Console.Write(currentNode.Value + " ");
            while (currentNode.rchild != head)
            {
                currentNode = Inorder_successor(ref currentNode);
                Console.Write(currentNode.Value + " ");
            }
        }

        public void Inorder_retraversal()
        {
            if (head.lchild == head)
            {
                Console.WriteLine("Tree is empty");
                return;
            }
            Node currentNode;
            currentNode = head.lchild;
            while (currentNode.rthread == 1)
            {
                currentNode = currentNode.rchild;
            }
            Console.Write(currentNode.Value + " ");
            while (currentNode.lchild != head)
            {
                currentNode = Inorder_per(ref currentNode);
                Console.Write(currentNode.Value + " ");
            }
        }

        public void remove(int element)
        {
            if (head.lchild == head)
            {
                Console.Write("tree is empty");
                return;
            }
            //find del node & it's parent node
            Node parent,currentNode,child=null;
            currentNode = head.lchild;
            parent = head;
            while (currentNode.Value!=element&&currentNode != null)
            {
                parent = currentNode;
                if (element < currentNode.Value && currentNode.lthread == 1)
                    currentNode = currentNode.lchild;
                else if (element < currentNode.Value && currentNode.lthread == 0)
                    currentNode = null;
                else if (element > currentNode.Value && currentNode.rthread == 1)
                    currentNode = currentNode.rchild;
                else if (element > currentNode.Value && currentNode.rthread == 0)
                    currentNode = null;               
            }
            if (currentNode == null)
            {
                Console.WriteLine("cannot find {0}", element);
                return;
            }
            while (true)
            {
                //前驱和 后继
                Node i_per;
                Node i_suc;
                //leaf
                if (currentNode.lthread == currentNode.rthread && currentNode.lthread == 0)
                {
                    if (parent == head)
                    {
                        head.lthread = 0;
                        head.lchild = head;
                    }
                    else if (currentNode == parent.lchild)
                    {
                        parent.lthread = 0;
                        parent.lchild = Inorder_per(ref currentNode);
                    }
                    else if (currentNode == parent.rchild)
                    {
                        parent.rthread = 0;
                        parent.rchild = Inorder_successor(ref currentNode);
                    }
                    break;
                }
                    //case2 has only one child
                else if ((currentNode.lthread == 0 && currentNode.rthread == 1)
                    || (currentNode.lthread == 1 && currentNode.rthread == 0))
                {
                     i_per = Inorder_per(ref currentNode);
                     i_suc = Inorder_successor(ref currentNode);
                    //has left child
                    if (currentNode.lthread == 1)
                    {
                        child = currentNode.lchild;
                    }
                    else if (currentNode.rthread == 1)
                    {
                        child = currentNode.rchild;
                    }

                    if (currentNode == parent.lchild)
                    {
                        parent.lchild = child;
                    }
                    else if (currentNode == parent.rchild)
                    {
                        parent.rchild = child;
                    }
                    //move
                    if (currentNode.rthread == 1)
                    {
                        i_suc.lchild = i_per;
                        i_suc.lthread = 0;
                    }
                    else if (currentNode.lthread == 1)
                    {
                        i_per.rchild = i_suc;
                        i_per.rthread = 0;
                    }
                    break;
                }
                else//case3 has two children
                {

                    i_suc = currentNode;
                    Inorder_successor(ref i_suc);
                    //中序后继的父节点
                    parent = i_suc.rchild;
                    //兑换当前与中续后继的值
                    currentNode.Value = i_suc.Value;
                   
                    currentNode = i_suc;
                    continue;
                }

            }
            //free
            currentNode = null;
        }

        static void Main(string[] args)
        {
            ThreadBinarySearchTree t = new ThreadBinarySearchTree();
            t.insert(65);
            t.insert(40);
            t.insert(30);           
            t.insert(50);
            t.insert(45);
            t.insert(72);
            t.insert(69);
            t.insert(80);
           
            t.Inorder_traversal();
            Console.Write("\n");
            Console.WriteLine("删除 40");
            t.remove(40);
            t.Inorder_traversal();
        }
    }
}

posted @ 2008-02-28 17:41 Humtong 阅读(116) 评论(0) 编辑


posts - 14, comments - 11, trackbacks - 0, articles - 0

Copyright © Humtong