예제 #1
0
파일: AvlTree.cs 프로젝트: radtek/datawf
        public void SwitchNodes(IAvlNode oldNode, IAvlNode newNode)
        {
            if (oldNode == newNode)
            {
                return;
            }

            var oldBalance = oldNode.Balance;
            var newLeft    = newNode.Left;
            var newRight   = newNode.Right;
            var oldParent  = oldNode.Parent;

            oldNode.Balance = newNode.Balance;
            newNode.Balance = oldBalance;

            // oldNode and newNode are Parent and Child
            if (newNode.Parent == oldNode)
            {
                if (oldNode.Parent != null)
                {
                    if (oldNode.Parent.Right == oldNode)
                    {
                        oldNode.Parent.Right = newNode;
                    }
                    else
                    {
                        oldNode.Parent.Left = newNode;
                    }
                }
                else if (oldNode == Root)
                {
                    Root = (T)newNode;
                }
                newNode.Parent = oldNode.Parent;
                oldNode.Parent = newNode;

                if (oldNode.Left == newNode)
                {
                    // update Children
                    newNode.Left  = oldNode;
                    newNode.Right = oldNode.Right;
                    oldNode.Left  = newLeft;
                    oldNode.Right = newRight;

                    // update Parents of Children
                    if (newNode.Right != null)
                    {
                        newNode.Right.Parent = newNode;
                    }
                    if (oldNode.Right != null)
                    {
                        oldNode.Right.Parent = oldNode;
                    }
                    if (oldNode.Left != null)
                    {
                        oldNode.Left.Parent = oldNode;
                    }
                }
                else
                { //odlNode.Right == newNode
                  // update Children
                    newNode.Right = oldNode;
                    newNode.Left  = oldNode.Left;
                    oldNode.Left  = newLeft;
                    oldNode.Right = newRight;

                    // update Parents of Children
                    if (newNode.Left != null)
                    {
                        newNode.Left.Parent = newNode;
                    }
                    if (oldNode.Right != null)
                    {
                        oldNode.Right.Parent = oldNode;
                    }
                    if (oldNode.Left != null)
                    {
                        oldNode.Left.Parent = oldNode;
                    }
                }
                return;
            }
            if (oldNode.Parent == newNode)
            {
                if (newNode.Parent != null)
                {
                    if (newNode.Parent.Right == newNode)
                    {
                        newNode.Parent.Right = oldNode;
                    }
                    else
                    {
                        newNode.Parent.Left = oldNode;
                    }
                }
                else if (newNode == Root)
                {
                    Root = (T)oldNode;
                }
                oldNode.Parent = newNode.Parent;
                newNode.Parent = oldNode;

                if (newNode.Left == oldNode)
                {
                    // update Children
                    newNode.Left  = oldNode.Left;
                    newNode.Right = oldNode.Right;
                    oldNode.Left  = newNode;
                    oldNode.Right = newRight;

                    // update Parents of Children
                    if (newNode.Right != null)
                    {
                        newNode.Right.Parent = newNode;
                    }
                    if (newNode.Left != null)
                    {
                        newNode.Left.Parent = newNode;
                    }
                    if (oldNode.Right != null)
                    {
                        oldNode.Right.Parent = oldNode;
                    }
                }
                else
                {
                    // update Children
                    newNode.Left  = oldNode.Left;
                    newNode.Right = oldNode.Right;
                    oldNode.Left  = newLeft;
                    oldNode.Right = newNode;

                    // update Parents of Children
                    if (newNode.Right != null)
                    {
                        newNode.Right.Parent = newNode;
                    }
                    if (newNode.Left != null)
                    {
                        newNode.Left.Parent = newNode;
                    }
                    if (oldNode.Left != null)
                    {
                        oldNode.Left.Parent = oldNode;
                    }
                }
                return;
            }

            // no node is Parent of the other

            // update Parents
            if (oldNode.AvlGetSibling() == newNode)
            {
                if (newNode.Parent.Right == newNode)
                {
                    newNode.Parent.Right = oldNode;
                    newNode.Parent.Left  = newNode;
                }
                else
                {
                    newNode.Parent.Left  = oldNode;
                    newNode.Parent.Right = newNode;
                }
            }
            else
            {
                oldNode.Parent = newNode.Parent;
                if (newNode.Parent != null)
                {
                    if (newNode.Parent.Right == newNode)
                    {
                        newNode.Parent.Right = oldNode;
                    }
                    else
                    {
                        newNode.Parent.Left = oldNode;
                    }
                }
                else if (newNode == Root)
                {
                    Root = (T)oldNode;
                }
                newNode.Parent = oldParent;
                if (oldParent != null)
                {
                    if (oldParent.Right == oldNode)
                    {
                        oldParent.Right = newNode;
                    }
                    else
                    {
                        oldParent.Left = newNode;
                    }
                }
                else if (oldNode == Root)
                {
                    Root = (T)newNode;
                }
            }
            // assign Children of newNode
            newNode.Left = oldNode.Left;
            if (newNode.Left != null)
            {
                newNode.Left.Parent = newNode;
            }
            newNode.Right = oldNode.Right;
            if (newNode.Right != null)
            {
                newNode.Right.Parent = newNode;
            }

            // assign Children of oldNode
            oldNode.Left = newLeft;
            if (oldNode.Left != null)
            {
                oldNode.Left.Parent = oldNode;
            }
            oldNode.Right = newRight;
            if (oldNode.Right != null)
            {
                oldNode.Right.Parent = oldNode;
            }
        }