private void RebalancePostDeletion(RBTreeNode node) { // Very similar to RebalancePostInsertion function // node is the node in the location of/closest to the node just deleted RBTreeNode s; // represents sibbling of node while (node != Root && node.IsBlack()) { if (node == node.Parent().Left()) { s = node.Parent().Right(); if (s.IsRed()) // case 1 { s.SetBlack(); node.Parent().SetRed(); RotateLeft(node.Parent()); s = node.Parent().Right(); } if (s.Left().IsBlack() && s.Right().IsBlack()) // case 2 { s.SetRed(); node = node.Parent(); } else { if (s.Right().IsBlack()) // case 3 { s.Left().SetBlack(); s.SetRed(); RotateRight(s); s = node.Parent().Right(); } if (s.Parent().IsRed()) { s.SetRed(); } else { s.SetBlack(); } node.Parent().SetBlack(); s.Right().SetBlack(); RotateLeft(s.Parent()); node = Root; } } else { s = node.Parent().Left(); if (s.IsRed()) { s.SetBlack(); node.Parent().SetRed(); RotateRight(node.Parent()); s = node.Parent().Left(); } if (s.Right() == null) { s.SetRight(Leaf); } if (s.Left() == null) { s.SetLeft(Leaf); } if (s.Right().IsBlack() && s.Left().IsBlack()) { s.SetRed(); node = node.Parent(); } else { if (s.Left().IsBlack()) { s.Right().SetBlack(); s.SetRed(); RotateLeft(s); s = node.Parent().Left(); } if (s.Parent().IsRed()) { s.SetRed(); } else { s.SetBlack(); } node.Parent().SetBlack(); s.Left().SetBlack(); RotateRight(node.Parent()); node = Root; } } } node.SetBlack(); }