Example #1
0
        public void Add(T node)
        {
            if (Root == null)
            {
                Count = 1;
                Root  = node;
                FixTreeOnInsert(node);
                return;
            }

            IRedBlackTreeNode parent = Root;

            while (true)
            {
                if (((IComparable)parent).CompareTo(node) <= 0)
                {
                    if (parent.Left == null)
                    {
                        InsertLeft(parent, node);
                        break;
                    }
                    parent = parent.Left;
                }
                else
                {
                    if (parent.Right == null)
                    {
                        InsertRight(parent, node);
                        break;
                    }
                    parent = parent.Right;
                }
            }
        }
Example #2
0
		void InternalRemove (IRedBlackTreeNode node)
		{
			if (node.Left != null && node.Right != null) {
				IRedBlackTreeNode outerLeft = node.Right.GetOuterLeft ();
				InternalRemove (outerLeft);
				Replace (node, outerLeft);
				
				outerLeft.Color = node.Color;
				outerLeft.Left = node.Left;
				if (outerLeft.Left != null)
					outerLeft.Left.Parent = outerLeft;
				
				outerLeft.Right = node.Right;
				if (outerLeft.Right != null)
					outerLeft.Right.Parent = outerLeft;
				outerLeft.UpdateAugmentedData ();
				return;
			}
			Count--;
			// node has only one child
			IRedBlackTreeNode child = node.Left ?? node.Right;
			
			Replace (node, child);
			
			if (node.Color == RedBlackColor.Black && child != null) {
				if (child.Color == RedBlackColor.Red) {
					child.Color = RedBlackColor.Black;
				} else {
					DeleteOneChild (child);
				}
			}
		}
Example #3
0
		public static T GetUncle<T> (this T node) where T : class, IRedBlackTreeNode
		{
			IRedBlackTreeNode grandparent = node.GetGrandparent ();
			if (grandparent == null)
				return null;
			return (T)(node.Parent == grandparent.Left ? grandparent.Right : grandparent.Left);
		}
Example #4
0
		public static T GetOuterLeft<T> (this T node) where T : class, IRedBlackTreeNode
		{
			IRedBlackTreeNode result = node;
			while (result.Left != null)
				result = result.Left;
			return (T)result;
		}
Example #5
0
        public void Remove(IRedBlackTreeNode node)
        {
            if (node.Left != null && node.Right != null)
            {
                IRedBlackTreeNode outerLeft = node.Right.GetOuterLeft();
                InternalRemove(outerLeft);
                Replace(node, outerLeft);

                outerLeft.Color = node.Color;
                outerLeft.Left  = node.Left;
                if (outerLeft.Left != null)
                {
                    outerLeft.Left.Parent = outerLeft;
                }

                outerLeft.Right = node.Right;
                if (outerLeft.Right != null)
                {
                    outerLeft.Right.Parent = outerLeft;
                }
                outerLeft.UpdateAugmentedData();
                OnNodeRemoved(new RedBlackTreeNodeEventArgs((T)node));
                return;
            }
            InternalRemove(node);
            OnNodeRemoved(new RedBlackTreeNodeEventArgs((T)node));
        }
Example #6
0
        static void AppendNode(StringBuilder builder, IRedBlackTreeNode node, int indent)
        {
            builder.Append(GetIndent(indent) + "Node (" + (node.Color == RedBlackColor.Red ? "r" : "b") + "):" + node + Environment.NewLine);
            builder.Append(GetIndent(indent) + "Left: ");
            if (node.Left != null)
            {
                builder.Append(Environment.NewLine);
                AppendNode(builder, node.Left, indent + 1);
            }
            else
            {
                builder.Append("null");
            }

            builder.Append(Environment.NewLine);
            builder.Append(GetIndent(indent) + "Right: ");
            if (node.Right != null)
            {
                builder.Append(Environment.NewLine);
                AppendNode(builder, node.Right, indent + 1);
            }
            else
            {
                builder.Append("null");
            }
        }
Example #7
0
		public void InsertBefore (IRedBlackTreeNode node, IRedBlackTreeNode newNode)
		{
			if (node.Left == null) {
				InsertLeft (node, newNode);
			} else {
				InsertRight (node.Left.GetOuterRight (), newNode);
			}
		}
Example #8
0
		public static T GetOuterRight<T> (this T node) where T : class, IRedBlackTreeNode
		{
			IRedBlackTreeNode result = node;
			while (result.Right != null) {
				result = result.Right;
			}
			return (T)result;
		}
Example #9
0
 public void InsertRight(IRedBlackTreeNode parentNode, IRedBlackTreeNode newNode)
 {
     parentNode.Right = newNode;
     newNode.Parent   = parentNode;
     newNode.Color    = RedBlackColor.Red;
     parentNode.UpdateAugmentedData();
     FixTreeOnInsert(newNode);
     Count++;
 }
Example #10
0
 public void InsertAfter(IRedBlackTreeNode node, IRedBlackTreeNode newNode)
 {
     if (node.Right == null)
     {
         InsertRight(node, newNode);
     }
     else
     {
         InsertLeft(node.Right.GetOuterLeft(), newNode);
     }
 }
Example #11
0
		void RotateRight (IRedBlackTreeNode node)
		{
			IRedBlackTreeNode left = node.Left;
			Replace (node, left);
			node.Left = left.Right;
			if (node.Left != null)
				node.Left.Parent = node;
			left.Right = node;
			node.Parent = left;
			node.UpdateAugmentedData ();
			node.Parent.UpdateAugmentedData ();
		}
Example #12
0
		void RotateLeft (IRedBlackTreeNode node)
		{
			IRedBlackTreeNode right = node.Right;
			Replace (node, right);
			node.Right = right.Left;
			if (node.Right != null)
				node.Right.Parent = node;
			right.Left = node;
			node.Parent = right;
			node.UpdateAugmentedData ();
			node.Parent.UpdateAugmentedData ();
		}
Example #13
0
		public static T GetNextNode<T> (this T node) where T : class, IRedBlackTreeNode
		{
			if (node.Right == null) {
				IRedBlackTreeNode curNode = node;
				IRedBlackTreeNode oldNode;
				do {
					oldNode = curNode;
					curNode = curNode.Parent;
				} while (curNode != null && curNode.Right == oldNode);
				return (T)curNode;
			}
			return (T)node.Right.GetOuterLeft ();
		}
Example #14
0
        void FixTreeOnInsert(IRedBlackTreeNode node)
        {
            var parent = node.Parent;

            if (parent == null)
            {
                node.Color = RedBlackColor.Black;
                return;
            }

            if (parent.Color == RedBlackColor.Black)
            {
                return;
            }
            var uncle = node.GetUncle();
            IRedBlackTreeNode grandParent = parent.Parent;

            if (uncle != null && uncle.Color == RedBlackColor.Red)
            {
                parent.Color      = RedBlackColor.Black;
                uncle.Color       = RedBlackColor.Black;
                grandParent.Color = RedBlackColor.Red;
                FixTreeOnInsert(grandParent);
                return;
            }

            if (node == parent.Right && parent == grandParent.Left)
            {
                RotateLeft(parent);
                node = node.Left;
            }
            else if (node == parent.Left && parent == grandParent.Right)
            {
                RotateRight(parent);
                node = node.Right;
            }

            parent      = node.Parent;
            grandParent = parent.Parent;

            parent.Color      = RedBlackColor.Black;
            grandParent.Color = RedBlackColor.Red;
            if (node == parent.Left && parent == grandParent.Left)
            {
                RotateRight(grandParent);
            }
            else
            {
                RotateLeft(grandParent);
            }
        }
Example #15
0
		void Replace (IRedBlackTreeNode oldNode, IRedBlackTreeNode newNode)
		{
			if (newNode != null)
				newNode.Parent = oldNode.Parent;
			if (oldNode.Parent == null) {
				Root = (T)newNode;
			} else {
				if (oldNode.Parent.Left == oldNode)
					oldNode.Parent.Left = newNode;
				else
					oldNode.Parent.Right = newNode;
				oldNode.Parent.UpdateAugmentedData ();
			}
		}
Example #16
0
 public static T GetPrevNode <T>(this T node) where T : class, IRedBlackTreeNode <T>
 {
     if (node.Left == null)
     {
         IRedBlackTreeNode <T> curNode = node;
         IRedBlackTreeNode <T> oldNode;
         do
         {
             oldNode = curNode;
             curNode = curNode.Parent;
         } while (curNode != null && curNode.Left == oldNode);
         return((T)curNode);
     }
     return((T)node.Left.GetOuterRight());
 }
Example #17
0
        private void AssertNode <T>(T expectedValue, bool expectedIsRed, bool expectedIsLeaf, IRedBlackTreeNode <T> actualNode)
        {
            Assert.Equal(expectedValue, actualNode.Value);

            if (expectedIsRed)
            {
                Assert.False(actualNode.IsBlack);
                Assert.True(actualNode.IsRed);
            }
            else
            {
                Assert.True(actualNode.IsBlack);
                Assert.False(actualNode.IsRed);
            }

            if (expectedIsLeaf)
            {
                Assert.True(actualNode.IsLeaf);
            }
            else
            {
                Assert.False(actualNode.IsLeaf);
            }
        }
Example #18
0
        void DeleteOneChild(IRedBlackTreeNode node)
        {
            // case 1
            if (node == null || node.Parent == null)
            {
                return;
            }

            var parent  = node.Parent;
            var sibling = node.GetSibling();

            if (sibling == null)
            {
                return;
            }

            // case 2
            if (sibling.Color == RedBlackColor.Red)
            {
                parent.Color  = RedBlackColor.Red;
                sibling.Color = RedBlackColor.Black;
                if (node == parent.Left)
                {
                    RotateLeft(parent);
                }
                else
                {
                    RotateRight(parent);
                }
                sibling = node.GetSibling();
                if (sibling == null)
                {
                    return;
                }
            }

            // case 3
            if (parent.Color == RedBlackColor.Black && sibling.Color == RedBlackColor.Black && GetColorSafe(sibling.Left) == RedBlackColor.Black && GetColorSafe(sibling.Right) == RedBlackColor.Black)
            {
                sibling.Color = RedBlackColor.Red;
                DeleteOneChild(parent);
                return;
            }

            // case 4
            if (parent.Color == RedBlackColor.Red && sibling.Color == RedBlackColor.Black && GetColorSafe(sibling.Left) == RedBlackColor.Black && GetColorSafe(sibling.Right) == RedBlackColor.Black)
            {
                sibling.Color = RedBlackColor.Red;
                parent.Color  = RedBlackColor.Black;
                return;
            }

            // case 5
            if (node == parent.Left && sibling.Color == RedBlackColor.Black && GetColorSafe(sibling.Left) == RedBlackColor.Red && GetColorSafe(sibling.Right) == RedBlackColor.Black)
            {
                sibling.Color = RedBlackColor.Red;
                if (sibling.Left != null)
                {
                    sibling.Left.Color = RedBlackColor.Black;
                }
                RotateRight(sibling);
            }
            else if (node == parent.Right && sibling.Color == RedBlackColor.Black && GetColorSafe(sibling.Right) == RedBlackColor.Red && GetColorSafe(sibling.Left) == RedBlackColor.Black)
            {
                sibling.Color = RedBlackColor.Red;
                if (sibling.Right != null)
                {
                    sibling.Right.Color = RedBlackColor.Black;
                }
                RotateLeft(sibling);
            }

            // case 6
            sibling = node.GetSibling();
            if (sibling == null)
            {
                return;
            }
            sibling.Color = parent.Color;
            parent.Color  = RedBlackColor.Black;
            if (node == parent.Left)
            {
                if (sibling.Right != null)
                {
                    sibling.Right.Color = RedBlackColor.Black;
                }
                RotateLeft(parent);
            }
            else
            {
                if (sibling.Left != null)
                {
                    sibling.Left.Color = RedBlackColor.Black;
                }
                RotateRight(parent);
            }
        }
Example #19
0
 public static bool IsLeaf(this IRedBlackTreeNode node)
 {
     return(node.Left == null && node.Right == null);
 }
Example #20
0
 static RedBlackColor GetColorSafe(IRedBlackTreeNode node)
 {
     return(node != null ? node.Color : RedBlackColor.Black);
 }