Deletion in Red-Black Tree

Deletion in a red-black tree is a bit more complicated than insertion. When a node is to be deleted, it can either have no children, one child or two children.

Here are the steps involved in deleting a node in a red-black tree:

1. If the node to be deleted has no children, simply remove it and update the parent node.
2. If the node to be deleted has only one child, replace the node with its child.
3. If the node to be deleted has two children, then replace the node with its in-order successor, which is the leftmost node in the right subtree. Then delete the in-order successor node as if it has at most one child.
4. After the node is deleted, the red-black properties might be violated. To restore these properties, some color changes and rotations are performed on the nodes in the tree. The changes are similar to those performed during insertion, but with different conditions.
5. The deletion operation in a red-black tree takes O(log n) time on average, making it a good choice for searching and deleting elements in large data sets.

Reference books for more information on Red-Black Trees and their implementation in various programming languages:

1. “Introduction to Algorithms” by Thomas H. Cormen, Charles E. Leiserson, Ronald L. Rivest, and Clifford Stein
2. “The Art of Computer Programming, Volume 3: Sorting and Searching” by Donald E. Knuth
3. “Algorithms in C, Part 5: Graph Algorithms” by Robert Sedgewick.

We have discussed the following topics on the Red-Black tree in previous posts. We strongly recommend referring following post as a prerequisite of this post.
Red-Black Tree IntroductionÂ
Red Black Tree Insert

Insertion Vs Deletion:Â
Like Insertion, recoloring and rotations are used to maintain the Red-Black properties.
In the insert operation, we check the color of the uncle to decide the appropriate case. In the delete operation, we check the color of the sibling to decide the appropriate case.
The main property that violates after insertion is two consecutive reds. In delete, the main violated property is, change of black height in subtrees as deletion of a black node may cause reduced black height in one root to leaf path.
Deletion is a fairly complex process.Â  To understand deletion, the notion of double black is used.Â  When a black node is deleted and replaced by a black child, the child is marked as double black. The main task now becomes to convert this double black to single black.
Deletion StepsÂ
Following are detailed steps for deletion.
1) Perform standard BST delete. When we perform standard delete operation in BST, we always end up deleting a node which is an either leaf or has only one child (For an internal node, we copy the successor and then recursively call delete for successor, successor is always a leaf node or a node with one child). So we only need to handle cases where a node is leaf or has one child. Let v be the node to be deleted and u be the child that replaces v (Note that u is NULL when v is a leaf and color of NULL is considered as Black).
2) Simple Case: If either u or v is red, we mark the replaced child as black (No change in black height). Note that both u and v cannot be red as v is parent of u and two consecutive reds are not allowed in red-black tree.Â
Â

3) If Both u and v are Black.
3.1) Color u as double black.Â  Now our task reduces to convert this double black to single black. Note that If v is leaf, then u is NULL and color of NULL is considered black. So the deletion of a black leaf also causes a double black.
Â

3.2) Do following while the current node u is double black, and it is not the root. Let sibling of node be s.Â
….(a): If sibling s is black and at least one of sibling’s children is red, perform rotation(s). Let the red child of s be r. This case can be divided in four subcases depending upon positions of s and r.
…………..(i) Left Left Case (s is left child of its parent and r is left child of s or both children of s are red). This is mirror of right right case shown in below diagram.
…………..(ii) Left Right Case (s is left child of its parent and r is right child). This is mirror of right left case shown in below diagram.
…………..(iii) Right Right Case (s is right child of its parent and r is right child of s or both children of s are red)Â
Â

…………..(iv) Right Left Case (s is right child of its parent and r is left child of s)Â
Â

…..(b): If sibling is black and its both children are black, perform recoloring, and recur for the parent if parent is black.Â
Â

In this case, if parent was red, then we didn’t need to recur for parent, we can simply make it black (red + double black = single black)
…..(c): If sibling is red, perform a rotation to move old sibling up, recolor the old sibling and parent. The new sibling is always black (See the below diagram). This mainly converts the tree to black sibling case (by rotation) and leads to case (a) or (b). This case can be divided in two subcases.Â
…………..(i) Left Case (s is left child of its parent). This is mirror of right right case shown in below diagram. We right rotate the parent p.Â
…………..(ii) Right Case (s is right child of its parent). We left rotate the parent p.Â
Â

3.3) If u is root, make it single black and return (Black height of complete tree reduces by 1).
below is the C++ implementation of above approach:Â
Â

CPP

 `#include ``#include ``using` `namespace` `std;` `enum` `COLOR { RED, BLACK };` `class` `Node {``public``:``  ``int` `val;``  ``COLOR color;``  ``Node *left, *right, *parent;` `  ``Node(``int` `val) : val(val) {``    ``parent = left = right = NULL;` `    ``// Node is created during insertion``    ``// Node is red at insertion``    ``color = RED;``  ``}` `  ``// returns pointer to uncle``  ``Node *uncle() {``    ``// If no parent or grandparent, then no uncle``    ``if` `(parent == NULL or parent->parent == NULL)``      ``return` `NULL;` `    ``if` `(parent->isOnLeft())``      ``// uncle on right``      ``return` `parent->parent->right;``    ``else``      ``// uncle on left``      ``return` `parent->parent->left;``  ``}` `  ``// check if node is left child of parent``  ``bool` `isOnLeft() { ``return` `this` `== parent->left; }` `  ``// returns pointer to sibling``  ``Node *sibling() {``    ``// sibling null if no parent``    ``if` `(parent == NULL)``      ``return` `NULL;` `    ``if` `(isOnLeft())``      ``return` `parent->right;` `    ``return` `parent->left;``  ``}` `  ``// moves node down and moves given node in its place``  ``void` `moveDown(Node *nParent) {``    ``if` `(parent != NULL) {``      ``if` `(isOnLeft()) {``        ``parent->left = nParent;``      ``} ``else` `{``        ``parent->right = nParent;``      ``}``    ``}``    ``nParent->parent = parent;``    ``parent = nParent;``  ``}` `  ``bool` `hasRedChild() {``    ``return` `(left != NULL and left->color == RED) or``           ``(right != NULL and right->color == RED);``  ``}``};` `class` `RBTree {``  ``Node *root;` `  ``// left rotates the given node``  ``void` `leftRotate(Node *x) {``    ``// new parent will be node's right child``    ``Node *nParent = x->right;` `    ``// update root if current node is root``    ``if` `(x == root)``      ``root = nParent;` `    ``x->moveDown(nParent);` `    ``// connect x with new parent's left element``    ``x->right = nParent->left;``    ``// connect new parent's left element with node``    ``// if it is not null``    ``if` `(nParent->left != NULL)``      ``nParent->left->parent = x;` `    ``// connect new parent with x``    ``nParent->left = x;``  ``}` `  ``void` `rightRotate(Node *x) {``    ``// new parent will be node's left child``    ``Node *nParent = x->left;` `    ``// update root if current node is root``    ``if` `(x == root)``      ``root = nParent;` `    ``x->moveDown(nParent);` `    ``// connect x with new parent's right element``    ``x->left = nParent->right;``    ``// connect new parent's right element with node``    ``// if it is not null``    ``if` `(nParent->right != NULL)``      ``nParent->right->parent = x;` `    ``// connect new parent with x``    ``nParent->right = x;``  ``}` `  ``void` `swapColors(Node *x1, Node *x2) {``    ``COLOR temp;``    ``temp = x1->color;``    ``x1->color = x2->color;``    ``x2->color = temp;``  ``}` `  ``void` `swapValues(Node *u, Node *v) {``    ``int` `temp;``    ``temp = u->val;``    ``u->val = v->val;``    ``v->val = temp;``  ``}` `  ``// fix red red at given node``  ``void` `fixRedRed(Node *x) {``    ``// if x is root color it black and return``    ``if` `(x == root) {``      ``x->color = BLACK;``      ``return``;``    ``}` `    ``// initialize parent, grandparent, uncle``    ``Node *parent = x->parent, *grandparent = parent->parent,``         ``*uncle = x->uncle();` `    ``if` `(parent->color != BLACK) {``      ``if` `(uncle != NULL && uncle->color == RED) {``        ``// uncle red, perform recoloring and recurse``        ``parent->color = BLACK;``        ``uncle->color = BLACK;``        ``grandparent->color = RED;``        ``fixRedRed(grandparent);``      ``} ``else` `{``        ``// Else perform LR, LL, RL, RR``        ``if` `(parent->isOnLeft()) {``          ``if` `(x->isOnLeft()) {``            ``// for left right``            ``swapColors(parent, grandparent);``          ``} ``else` `{``            ``leftRotate(parent);``            ``swapColors(x, grandparent);``          ``}``          ``// for left left and left right``          ``rightRotate(grandparent);``        ``} ``else` `{``          ``if` `(x->isOnLeft()) {``            ``// for right left``            ``rightRotate(parent);``            ``swapColors(x, grandparent);``          ``} ``else` `{``            ``swapColors(parent, grandparent);``          ``}` `          ``// for right right and right left``          ``leftRotate(grandparent);``        ``}``      ``}``    ``}``  ``}` `  ``// find node that do not have a left child``  ``// in the subtree of the given node``  ``Node *successor(Node *x) {``    ``Node *temp = x;` `    ``while` `(temp->left != NULL)``      ``temp = temp->left;` `    ``return` `temp;``  ``}` `  ``// find node that replaces a deleted node in BST``  ``Node *BSTreplace(Node *x) {``    ``// when node have 2 children``    ``if` `(x->left != NULL and x->right != NULL)``      ``return` `successor(x->right);` `    ``// when leaf``    ``if` `(x->left == NULL and x->right == NULL)``      ``return` `NULL;` `    ``// when single child``    ``if` `(x->left != NULL)``      ``return` `x->left;``    ``else``      ``return` `x->right;``  ``}` `  ``// deletes the given node``  ``void` `deleteNode(Node *v) {``    ``Node *u = BSTreplace(v);` `    ``// True when u and v are both black``    ``bool` `uvBlack = ((u == NULL or u->color == BLACK) and (v->color == BLACK));``    ``Node *parent = v->parent;` `    ``if` `(u == NULL) {``      ``// u is NULL therefore v is leaf``      ``if` `(v == root) {``        ``// v is root, making root null``        ``root = NULL;``      ``} ``else` `{``        ``if` `(uvBlack) {``          ``// u and v both black``          ``// v is leaf, fix double black at v``          ``fixDoubleBlack(v);``        ``} ``else` `{``          ``// u or v is red``          ``if` `(v->sibling() != NULL)``            ``// sibling is not null, make it red"``            ``v->sibling()->color = RED;``        ``}` `        ``// delete v from the tree``        ``if` `(v->isOnLeft()) {``          ``parent->left = NULL;``        ``} ``else` `{``          ``parent->right = NULL;``        ``}``      ``}``      ``delete` `v;``      ``return``;``    ``}` `    ``if` `(v->left == NULL or v->right == NULL) {``      ``// v has 1 child``      ``if` `(v == root) {``        ``// v is root, assign the value of u to v, and delete u``        ``v->val = u->val;``        ``v->left = v->right = NULL;``        ``delete` `u;``      ``} ``else` `{``        ``// Detach v from tree and move u up``        ``if` `(v->isOnLeft()) {``          ``parent->left = u;``        ``} ``else` `{``          ``parent->right = u;``        ``}``        ``delete` `v;``        ``u->parent = parent;``        ``if` `(uvBlack) {``          ``// u and v both black, fix double black at u``          ``fixDoubleBlack(u);``        ``} ``else` `{``          ``// u or v red, color u black``          ``u->color = BLACK;``        ``}``      ``}``      ``return``;``    ``}` `    ``// v has 2 children, swap values with successor and recurse``    ``swapValues(u, v);``    ``deleteNode(u);``  ``}` `  ``void` `fixDoubleBlack(Node *x) {``    ``if` `(x == root)``      ``// Reached root``      ``return``;` `    ``Node *sibling = x->sibling(), *parent = x->parent;``    ``if` `(sibling == NULL) {``      ``// No sibling, double black pushed up``      ``fixDoubleBlack(parent);``    ``} ``else` `{``      ``if` `(sibling->color == RED) {``        ``// Sibling red``        ``parent->color = RED;``        ``sibling->color = BLACK;``        ``if` `(sibling->isOnLeft()) {``          ``// left case``          ``rightRotate(parent);``        ``} ``else` `{``          ``// right case``          ``leftRotate(parent);``        ``}``        ``fixDoubleBlack(x);``      ``} ``else` `{``        ``// Sibling black``        ``if` `(sibling->hasRedChild()) {``          ``// at least 1 red children``          ``if` `(sibling->left != NULL and sibling->left->color == RED) {``            ``if` `(sibling->isOnLeft()) {``              ``// left left``              ``sibling->left->color = sibling->color;``              ``sibling->color = parent->color;``              ``rightRotate(parent);``            ``} ``else` `{``              ``// right left``              ``sibling->left->color = parent->color;``              ``rightRotate(sibling);``              ``leftRotate(parent);``            ``}``          ``} ``else` `{``            ``if` `(sibling->isOnLeft()) {``              ``// left right``              ``sibling->right->color = parent->color;``              ``leftRotate(sibling);``              ``rightRotate(parent);``            ``} ``else` `{``              ``// right right``              ``sibling->right->color = sibling->color;``              ``sibling->color = parent->color;``              ``leftRotate(parent);``            ``}``          ``}``          ``parent->color = BLACK;``        ``} ``else` `{``          ``// 2 black children``          ``sibling->color = RED;``          ``if` `(parent->color == BLACK)``            ``fixDoubleBlack(parent);``          ``else``            ``parent->color = BLACK;``        ``}``      ``}``    ``}``  ``}` `  ``// prints level order for given node``  ``void` `levelOrder(Node *x) {``    ``if` `(x == NULL)``      ``// return if node is null``      ``return``;` `    ``// queue for level order``    ``queue q;``    ``Node *curr;` `    ``// push x``    ``q.push(x);` `    ``while` `(!q.empty()) {``      ``// while q is not empty``      ``// dequeue``      ``curr = q.front();``      ``q.pop();` `      ``// print node value``      ``cout << curr->val << ``" "``;` `      ``// push children to queue``      ``if` `(curr->left != NULL)``        ``q.push(curr->left);``      ``if` `(curr->right != NULL)``        ``q.push(curr->right);``    ``}``  ``}` `  ``// prints inorder recursively``  ``void` `inorder(Node *x) {``    ``if` `(x == NULL)``      ``return``;``    ``inorder(x->left);``    ``cout << x->val << ``" "``;``    ``inorder(x->right);``  ``}` `public``:``  ``// constructor``  ``// initialize root``  ``RBTree() { root = NULL; }` `  ``Node *getRoot() { ``return` `root; }` `  ``// searches for given value``  ``// if found returns the node (used for delete)``  ``// else returns the last node while traversing (used in insert)``  ``Node *search(``int` `n) {``    ``Node *temp = root;``    ``while` `(temp != NULL) {``      ``if` `(n < temp->val) {``        ``if` `(temp->left == NULL)``          ``break``;``        ``else``          ``temp = temp->left;``      ``} ``else` `if` `(n == temp->val) {``        ``break``;``      ``} ``else` `{``        ``if` `(temp->right == NULL)``          ``break``;``        ``else``          ``temp = temp->right;``      ``}``    ``}` `    ``return` `temp;``  ``}` `  ``// inserts the given value to tree``  ``void` `insert(``int` `n) {``    ``Node *newNode = ``new` `Node(n);``    ``if` `(root == NULL) {``      ``// when root is null``      ``// simply insert value at root``      ``newNode->color = BLACK;``      ``root = newNode;``    ``} ``else` `{``      ``Node *temp = search(n);` `      ``if` `(temp->val == n) {``        ``// return if value already exists``        ``return``;``      ``}` `      ``// if value is not found, search returns the node``      ``// where the value is to be inserted` `      ``// connect new node to correct node``      ``newNode->parent = temp;` `      ``if` `(n < temp->val)``        ``temp->left = newNode;``      ``else``        ``temp->right = newNode;` `      ``// fix red red violation if exists``      ``fixRedRed(newNode);``    ``}``  ``}` `  ``// utility function that deletes the node with given value``  ``void` `deleteByVal(``int` `n) {``    ``if` `(root == NULL)``      ``// Tree is empty``      ``return``;` `    ``Node *v = search(n), *u;` `    ``if` `(v->val != n) {``      ``cout << ``"No node found to delete with value:"` `<< n << endl;``      ``return``;``    ``}` `    ``deleteNode(v);``  ``}` `  ``// prints inorder of the tree``  ``void` `printInOrder() {``    ``cout << ``"Inorder: "` `<< endl;``    ``if` `(root == NULL)``      ``cout << ``"Tree is empty"` `<< endl;``    ``else``      ``inorder(root);``    ``cout << endl;``  ``}` `  ``// prints level order of the tree``  ``void` `printLevelOrder() {``    ``cout << ``"Level order: "` `<< endl;``    ``if` `(root == NULL)``      ``cout << ``"Tree is empty"` `<< endl;``    ``else``      ``levelOrder(root);``    ``cout << endl;``  ``}``};` `int` `main() {``  ``RBTree tree;` `  ``tree.insert(7);``  ``tree.insert(3);``  ``tree.insert(18);``  ``tree.insert(10);``  ``tree.insert(22);``  ``tree.insert(8);``  ``tree.insert(11);``  ``tree.insert(26);``  ``tree.insert(2);``  ``tree.insert(6);``  ``tree.insert(13);` `  ``tree.printInOrder();``  ``tree.printLevelOrder();` `  ``cout<

Java

 `// Java Code for the above approach` `import` `java.util.LinkedList;``import` `java.util.Queue;` `enum` `COLOR { RED, BLACK }` `class` `Node {``    ``int` `val;``    ``COLOR color;``    ``Node left, right, parent;` `    ``Node(``int` `val) {``        ``this``.val = val;``        ``parent = left = right = ``null``;``        ` `        ``// Node is created during insertion``        ``// Node is red at insertion``        ``color = COLOR.RED;``    ``}``    ` `    ``// returns pointer to uncle``    ``Node uncle() {``        ` `        ``// If no parent or grandparent, then no uncle``        ``if` `(parent == ``null` `|| parent.parent == ``null``)``            ``return` `null``;``        ` `        ``if` `(parent.isOnLeft())``            ``// uncle on right``            ``return` `parent.parent.right;``        ``else``        ``// uncle on left``            ``return` `parent.parent.left;``    ``}``    ` `      ``// check if node is left child of parent``    ``boolean` `isOnLeft() {``        ``return` `this` `== parent.left;``    ``}``    ` `    ``// returns pointer to sibling``    ``Node sibling() {``        ` `        ``// sibling null if no parent``        ``if` `(parent == ``null``)``            ``return` `null``;` `        ``if` `(isOnLeft())``            ``return` `parent.right;` `        ``return` `parent.left;``    ``}``    ` `    ``// moves node down and moves given node in its place``    ``void` `moveDown(Node nParent) {``        ``if` `(parent != ``null``) {``            ``if` `(isOnLeft())``                ``parent.left = nParent;``            ``else``                ``parent.right = nParent;``        ``}``        ``nParent.parent = parent;``        ``parent = nParent;``    ``}` `    ``boolean` `hasRedChild() {``        ``return` `(left != ``null` `&& left.color == COLOR.RED) ||``                ``(right != ``null` `&& right.color == COLOR.RED);``    ``}``}` `class` `RBTree {``    ``Node root;``    ` `    ``// left rotates the given node``    ``void` `leftRotate(Node x) {``        ``// new parent will be node's right child``        ``Node nParent = x.right;``        ` `        ``// update root if current node is root``        ``if` `(x == root)``            ``root = nParent;``            ` `        ``x.moveDown(nParent);``        ` `        ``// connect x with new parent's left element``        ``x.right = nParent.left;``        ` `        ``// connect new parent's left element with node``        ``// if it is not null``        ``if` `(nParent.left != ``null``)``            ``nParent.left.parent = x;``        ` `        ``// connect new parent with x``        ``nParent.left = x;``    ``}` `    ``void` `rightRotate(Node x) {``        ` `        ``// new parent will be node's left child``        ``Node nParent = x.left;``        ` `        ``// update root if current node is root``        ``if` `(x == root)``            ``root = nParent;` `        ``x.moveDown(nParent);``        ` `        ``// connect x with new parent's right element``        ``x.left = nParent.right;``        ` `        ``// connect new parent's right element with node``        ``// if it is not null``        ``if` `(nParent.right != ``null``)``            ``nParent.right.parent = x;``        ` `        ``// connect new parent with x``        ``nParent.right = x;``    ``}` `    ``void` `swapColors(Node x1, Node x2) {``        ``COLOR temp = x1.color;``        ``x1.color = x2.color;``        ``x2.color = temp;``    ``}` `    ``void` `swapValues(Node u, Node v) {``        ``int` `temp = u.val;``        ``u.val = v.val;``        ``v.val = temp;``    ``}``    ` `    ``// fix red red at given node``    ``void` `fixRedRed(Node x) {``        ` `         ``// if x is root color it black and return``        ``if` `(x == root) {``            ``x.color = COLOR.BLACK;``            ``return``;``        ``}``        ` `        ``// initialize parent, grandparent, uncle``        ``Node parent = x.parent, grandparent = parent.parent, uncle = x.uncle();` `        ``if` `(parent.color != COLOR.BLACK) {``            ``if` `(uncle != ``null` `&& uncle.color == COLOR.RED) {``                ` `                ``// uncle red, perform recoloring and recurse``                ``parent.color = COLOR.BLACK;``                ``uncle.color = COLOR.BLACK;``                ``grandparent.color = COLOR.RED;``                ``fixRedRed(grandparent);``            ``} ``else` `{``                ``// Else perform LR, LL, RL, RR``                ``if` `(parent.isOnLeft()) {``                    ``if` `(x.isOnLeft())``                        ``// for left right``                        ``swapColors(parent, grandparent);``                    ``else` `{``                        ``leftRotate(parent);``                        ``swapColors(x, grandparent);``                    ``}``                    ``// for left left and left right``                    ``rightRotate(grandparent);``                ``} ``else` `{``                    ``if` `(x.isOnLeft()) {``                        ``// for right left``                        ``rightRotate(parent);``                        ``swapColors(x, grandparent);``                    ``} ``else``                        ``swapColors(parent, grandparent);``                        ` `                    ``// for right right and right left``                    ``leftRotate(grandparent);``                ``}``            ``}``        ``}``    ``}``    ``// find node that do not have a left child``    ``// in the subtree of the given node``    ``Node successor(Node x) {``        ``Node temp = x;``        ``while` `(temp.left != ``null``)``            ``temp = temp.left;``        ``return` `temp;``    ``}``    ` `    ``// find node that replaces a deleted node in BST``    ``Node BSTreplace(Node x) {``        ``// when node have 2 children``        ``if` `(x.left != ``null` `&& x.right != ``null``)``            ``return` `successor(x.right);``            ` `        ``// when leaf``        ``if` `(x.left == ``null` `&& x.right == ``null``)``            ``return` `null``;``            ` `        ``// when single child``        ``if` `(x.left != ``null``)``            ``return` `x.left;``        ``else``            ``return` `x.right;``    ``}``    ` `    ``// deletes the given node``    ``void` `deleteNode(Node v) {``        ``Node u = BSTreplace(v);``        ``// True when u and v are both black``        ``boolean` `uvBlack = ((u == ``null` `|| u.color == COLOR.BLACK) && (v.color == COLOR.BLACK));``        ``Node parent = v.parent;` `        ``if` `(u == ``null``) {``            ``// u is NULL therefore v is leaf``            ``if` `(v == root)``             ``// v is root, making root null``                ``root = ``null``;``            ``else` `{``                ``if` `(uvBlack)``                ``// u and v both black``                ``// v is leaf, fix double black at v``                    ``fixDoubleBlack(v);``                    ` `                ``// u or v is red``                ``else` `if` `(v.sibling() != ``null``)``                ``// sibling is not null, make it red``                    ``v.sibling().color = COLOR.RED;``                ` `                ``// delete v from the tree``                ``if` `(v.isOnLeft())``                    ``parent.left = ``null``;``                ``else``                    ``parent.right = ``null``;``            ``}``            ``return``;``        ``}` `        ``if` `(v.left == ``null` `|| v.right == ``null``) {``            ``// v has 1 child``            ``if` `(v == root) {``                ``// v is root, assign the value of u to v, and delete u``                ``v.val = u.val;``                ``v.left = v.right = ``null``;``                ``// delete u;``            ``} ``else` `{``                ``// Detach v from tree and move u up``                ``if` `(v.isOnLeft())``                    ``parent.left = u;``                ``else``                    ``parent.right = u;` `                ``u.parent = parent;` `                ``if` `(uvBlack)``                ``// u and v both black, fix double black at u``                    ``fixDoubleBlack(u);``                ``else``                ``// u or v red, color u black``                    ``u.color = COLOR.BLACK;``            ``}``            ``return``;``        ``}``        ` `        ``// v has 2 children, swap values with successor and recurse``        ``swapValues(u, v);``        ``deleteNode(u);``    ``}` `    ``void` `fixDoubleBlack(Node x) {``        ``// Reached root``        ``if` `(x == root)``            ``return``;` `        ``Node sibling = x.sibling(), parent = x.parent;` `        ``if` `(sibling == ``null``)``        ``// No sibling, double black pushed up``            ``fixDoubleBlack(parent);``        ``else` `{``            ``if` `(sibling.color == COLOR.RED) {``                ``// sibling red``                ``parent.color = COLOR.RED;``                ``sibling.color = COLOR.BLACK;` `                ``if` `(sibling.isOnLeft())``                    ``// right case``                    ``rightRotate(parent);``                ``else``                    ``// right case``                    ``leftRotate(parent);` `                ``fixDoubleBlack(x);``            ``} ``else` `{``                ``// Sibling black``                ``if` `(sibling.hasRedChild()) {``                    ``// at least 1 red children``                    ``if` `(sibling.left != ``null` `&& sibling.left.color == COLOR.RED) {``                        ``if` `(sibling.isOnLeft()) {``                            ``// left left``                            ``sibling.left.color = sibling.color;``                            ``sibling.color = parent.color;``                            ``rightRotate(parent);``                        ``} ``else` `{``                            ``// right right``                            ``sibling.left.color = parent.color;``                            ``rightRotate(sibling);``                            ``leftRotate(parent);``                        ``}``                    ``} ``else` `{``                        ``if` `(sibling.isOnLeft()) {``                            ``// left right``                            ``sibling.right.color = parent.color;``                            ``leftRotate(sibling);``                            ``rightRotate(parent);``                        ``} ``else` `{``                            ``// right right``                            ``sibling.right.color = sibling.color;``                            ``sibling.color = parent.color;``                            ``leftRotate(parent);``                        ``}``                    ``}``                    ``parent.color = COLOR.BLACK;``                ``} ``else` `{``                    ``// 2 black children``                    ``sibling.color = COLOR.RED;``                    ``if` `(parent.color == COLOR.BLACK)``                        ``fixDoubleBlack(parent);``                    ``else``                        ``parent.color = COLOR.BLACK;``                ``}``            ``}``        ``}``    ``}``    ` `    ``// prints level order for given node``    ``void` `levelOrder(Node x) {``        ``if` `(x == ``null``)``            ``return``;``        ` `        ``// queue for level order``        ``Queue q = ``new` `LinkedList<>();``        ``Node curr;` `        ``q.add(x);` `        ``while` `(!q.isEmpty()) {``            ``curr = q.poll();``            ``// print node value``            ``System.out.print(curr.val + ``" "``);``            ` `            ``// push children to queue``            ``if` `(curr.left != ``null``)``                ``q.add(curr.left);``            ``if` `(curr.right != ``null``)``                ``q.add(curr.right);``        ``}``    ``}``    ` `    ``// prints inorder recursively``    ``void` `inorder(Node x) {``        ``if` `(x == ``null``)``            ``return``;` `        ``inorder(x.left);``        ``System.out.print(x.val + ``" "``);``        ``inorder(x.right);``    ``}``    ` `    ``// constructor``    ``// initialize root``    ``RBTree() {``        ``root = ``null``;``    ``}` `    ``Node getRoot() {``        ``return` `root;``    ``}``    ` `    ``// searches for given value``    ``// if found returns the node (used for delete)``    ``// else returns the last node while traversing (used in insert)``    ``Node search(``int` `n) {``        ``Node temp = root;``        ``while` `(temp != ``null``) {``            ``if` `(n < temp.val) {``                ``if` `(temp.left == ``null``)``                    ``break``;``                ``else``                    ``temp = temp.left;``            ``} ``else` `if` `(n == temp.val) {``                ``break``;``            ``} ``else` `{``                ``if` `(temp.right == ``null``)``                    ``break``;``                ``else``                    ``temp = temp.right;``            ``}``        ``}` `        ``return` `temp;``    ``}``    ` `    ``// inserts the given value to tree``    ``void` `insert(``int` `n) {``        ``Node newNode = ``new` `Node(n);``        ``if` `(root == ``null``) {``            ``// when root is null``            ``// simply insert value at root``            ``newNode.color = COLOR.BLACK;``            ``root = newNode;``        ``} ``else` `{``            ``Node temp = search(n);``            ` `            ``// return if value already exists``            ``if` `(temp.val == n)``                ``return``;``                ` `            ``// if value is not found, search returns the node``            ``// where the value is to be inserted`` ` `            ``// connect new node to correct node``            ``newNode.parent = temp;` `            ``if` `(n < temp.val)``                ``temp.left = newNode;``            ``else``                ``temp.right = newNode;``            ` `            ``// fix red red violation if exists``            ``fixRedRed(newNode);``        ``}``    ``}``    ` `    ``// utility function that deletes the node with given value``    ``void` `deleteByVal(``int` `n) {``        ``if` `(root == ``null``)``            ``return``;` `        ``Node v = search(n), u;` `        ``if` `(v.val != n) {``            ``System.out.println(``"No node found to delete with value: "` `+ n);``            ``return``;``        ``}` `        ``deleteNode(v);``    ``}``    ` `    ``// prints inorder of the tree``    ``void` `printInOrder() {``        ``System.out.println(``"Inorder: "``);``        ``if` `(root == ``null``)``            ``System.out.println(``"Tree is empty"``);``        ``else``            ``inorder(root);``        ``System.out.println();``    ``}``    ` `    ``// prints level order of the tree``    ``void` `printLevelOrder() {``        ``System.out.println(``"Level order: "``);``        ``if` `(root == ``null``)``            ``System.out.println(``"Tree is empty"``);``        ``else``            ``levelOrder(root);``        ``System.out.println();``    ``}``}` `public` `class` `Main {``    ``public` `static` `void` `main(String[] args) {``        ``RBTree tree = ``new` `RBTree();` `        ``tree.insert(``7``);``        ``tree.insert(``3``);``        ``tree.insert(``18``);``        ``tree.insert(``10``);``        ``tree.insert(``22``);``        ``tree.insert(``8``);``        ``tree.insert(``11``);``        ``tree.insert(``26``);``        ``tree.insert(``2``);``        ``tree.insert(``6``);``        ``tree.insert(``13``);` `        ``tree.printInOrder();``        ``tree.printLevelOrder();` `        ``System.out.println(``"\nDeleting 18, 11, 3, 10, 22\n"``);` `        ``tree.deleteByVal(``18``);``        ``tree.deleteByVal(``11``);``        ``tree.deleteByVal(``3``);``        ``tree.deleteByVal(``10``);``        ``tree.deleteByVal(``22``);` `        ``tree.printInOrder();``        ``tree.printLevelOrder();``    ``}``}` `// This code is contributed by Abhinav Mahajan (abhinav_m22).`

Python3

 `# Python code for the above approach``from` `queue ``import` `Queue` `# Enumeration for colors``class` `COLOR:``    ``RED ``=` `'RED'``    ``BLACK ``=` `'BLACK'` `class` `Node:``    ``def` `__init__(``self``, val):``        ``# Initialize node attributes``        ``self``.val ``=` `val``        ``self``.color ``=` `COLOR.RED  ``# New nodes are always red``        ``self``.left ``=` `None``        ``self``.right ``=` `None``        ``self``.parent ``=` `None` `    ``def` `uncle(``self``):``        ``# Returns the uncle of the node``        ``if` `self``.parent ``is` `None` `or` `self``.parent.parent ``is` `None``:``            ``return` `None` `        ``if` `self``.parent.isOnLeft():``            ``return` `self``.parent.parent.right``        ``else``:``            ``return` `self``.parent.parent.left` `    ``def` `isOnLeft(``self``):``        ``# Checks if the node is the left child of its parent``        ``return` `self` `=``=` `self``.parent.left` `    ``def` `sibling(``self``):``        ``# Returns the sibling of the node``        ``if` `self``.parent ``is` `None``:``            ``return` `None` `        ``if` `self``.isOnLeft():``            ``return` `self``.parent.right``        ``else``:``            ``return` `self``.parent.left` `    ``def` `moveDown(``self``, new_parent):``        ``# Moves the node down by changing its parent``        ``if` `self``.parent ``is` `not` `None``:``            ``if` `self``.isOnLeft():``                ``self``.parent.left ``=` `new_parent``            ``else``:``                ``self``.parent.right ``=` `new_parent``        ``new_parent.parent ``=` `self``.parent``        ``self``.parent ``=` `new_parent` `    ``def` `hasRedChild(``self``):``        ``# Checks if the node has a red child``        ``return` `(``self``.left ``is` `not` `None` `and` `self``.left.color ``=``=` `COLOR.RED) ``or` `\``               ``(``self``.right ``is` `not` `None` `and` `self``.right.color ``=``=` `COLOR.RED)` `class` `RBTree:``    ``def` `__init__(``self``):``        ``# Initialize Red-Black Tree with an empty root``        ``self``.root ``=` `None` `    ``def` `leftRotate(``self``, x):``        ``# Performs a left rotation around the given node``        ``new_parent ``=` `x.right` `        ``if` `x ``=``=` `self``.root:``            ``self``.root ``=` `new_parent` `        ``x.moveDown(new_parent)` `        ``x.right ``=` `new_parent.left``        ``if` `new_parent.left ``is` `not` `None``:``            ``new_parent.left.parent ``=` `x` `        ``new_parent.left ``=` `x` `    ``def` `rightRotate(``self``, x):``        ``# Performs a right rotation around the given node``        ``new_parent ``=` `x.left` `        ``if` `x ``=``=` `self``.root:``            ``self``.root ``=` `new_parent` `        ``x.moveDown(new_parent)` `        ``x.left ``=` `new_parent.right``        ``if` `new_parent.right ``is` `not` `None``:``            ``new_parent.right.parent ``=` `x` `        ``new_parent.right ``=` `x` `    ``def` `swapColors(``self``, x1, x2):``        ``# Swaps the colors of two nodes``        ``temp ``=` `x1.color``        ``x1.color ``=` `x2.color``        ``x2.color ``=` `temp` `    ``def` `swapValues(``self``, u, v):``        ``# Swaps the values of two nodes``        ``temp ``=` `u.val``        ``u.val ``=` `v.val``        ``v.val ``=` `temp` `    ``def` `fixRedRed(``self``, x):``        ``# Fixes the red-red violation in the tree``        ``if` `x ``=``=` `self``.root:``            ``x.color ``=` `COLOR.BLACK``            ``return` `        ``parent ``=` `x.parent``        ``grandparent ``=` `parent.parent``        ``uncle ``=` `x.uncle()` `        ``if` `parent.color !``=` `COLOR.BLACK:``            ``if` `uncle ``is` `not` `None` `and` `uncle.color ``=``=` `COLOR.RED:``                ``# Uncle is red, perform recoloring and recurse``                ``parent.color ``=` `COLOR.BLACK``                ``uncle.color ``=` `COLOR.BLACK``                ``grandparent.color ``=` `COLOR.RED``                ``self``.fixRedRed(grandparent)``            ``else``:``                ``# Perform rotations based on the cases``                ``if` `parent.isOnLeft():``                    ``if` `x.isOnLeft():``                        ``self``.swapColors(parent, grandparent)``                    ``else``:``                        ``self``.leftRotate(parent)``                        ``self``.swapColors(x, grandparent)``                    ``self``.rightRotate(grandparent)``                ``else``:``                    ``if` `x.isOnLeft():``                        ``self``.rightRotate(parent)``                        ``self``.swapColors(x, grandparent)``                    ``else``:``                        ``self``.swapColors(parent, grandparent)``                    ``self``.leftRotate(grandparent)` `    ``def` `successor(``self``, x):``        ``# Finds the in-order successor of the given node``        ``temp ``=` `x` `        ``while` `temp.left ``is` `not` `None``:``            ``temp ``=` `temp.left` `        ``return` `temp` `    ``def` `BSTreplace(``self``, x):``        ``# Finds the replacement node in BST for the given node``        ``if` `x.left ``is` `not` `None` `and` `x.right ``is` `not` `None``:``            ``return` `self``.successor(x.right)` `        ``if` `x.left ``is` `None` `and` `x.right ``is` `None``:``            ``return` `None` `        ``if` `x.left ``is` `not` `None``:``            ``return` `x.left``        ``else``:``            ``return` `x.right` `    ``def` `deleteNode(``self``, v):``        ``# Deletes the given node from the tree``        ``u ``=` `self``.BSTreplace(v)``        ``uvBlack ``=` `(u ``is` `None` `or` `u.color ``=``=` `COLOR.BLACK) ``and` `(v.color ``=``=` `COLOR.BLACK)``        ``parent ``=` `v.parent` `        ``if` `u ``is` `None``:``            ``# Node to be deleted is a leaf or has only one child``            ``if` `v ``=``=` `self``.root:``                ``# If the node is the root``                ``self``.root ``=` `None``            ``else``:``                ``# Detach v from the tree and move u up``                ``if` `uvBlack:``                    ``# u and v both black, fix double black at v``                    ``self``.fixDoubleBlack(v)``                ``else``:``                    ``# u or v red, color u black``                    ``if` `v.sibling() ``is` `not` `None``:``                        ``v.sibling().color ``=` `COLOR.RED` `                ``if` `v.isOnLeft():``                    ``parent.left ``=` `None``                ``else``:``                    ``parent.right ``=` `None` `            ``del` `v  ``# Delete the node``            ``return` `        ``if` `v.left ``is` `None` `or` `v.right ``is` `None``:``            ``# Node to be deleted has only one child``            ``if` `v ``=``=` `self``.root:``                ``# If the node is the root``                ``v.val ``=` `u.val``                ``v.left ``=` `v.right ``=` `None``                ``del` `u``            ``else``:``                ``# Detach v from the tree and move u up``                ``if` `v.isOnLeft():``                    ``parent.left ``=` `u``                ``else``:``                    ``parent.right ``=` `u` `                ``del` `v``                ``u.parent ``=` `parent``                ``if` `uvBlack:``                    ``# u and v both black, fix double black at u``                    ``self``.fixDoubleBlack(u)``                ``else``:``                    ``# u or v red, color u black``                    ``u.color ``=` `COLOR.BLACK``        ``else``:``            ``# Node to be deleted has two children, swap values with successor and recurse``            ``self``.swapValues(u, v)``            ``self``.deleteNode(u)` `    ``# Fixes the double black violation in the tree``    ``def` `fixDoubleBlack(``self``, x):``        ` `        ``# Reached root``        ``if` `x ``=``=` `self``.root:``            ``return` `        ``sibling ``=` `x.sibling()``        ``parent ``=` `x.parent` `        ``# No sibling, double black pushed up``        ``if` `sibling ``is` `None``:``            ``self``.fixDoubleBlack(parent)``        ``else``:``            ` `            ``# Sibling red``            ``if` `sibling.color ``=``=` `COLOR.RED:``                ``parent.color ``=` `COLOR.RED``                ``sibling.color ``=` `COLOR.BLACK``                ` `                ``# Left case``                ``if` `sibling.isOnLeft():``                    ``self``.rightRotate(parent)``                ` `                ``# Right case``                ``else``:``                    ``self``.leftRotate(parent)``                ``self``.fixDoubleBlack(x)``            ``else``:``                ` `                ``# Sibling black``                ``if` `sibling.hasRedChild():``                    ` `                    ``# At least 1 red child``                    ``if` `sibling.left ``is` `not` `None` `and` `sibling.left.color ``=``=` `COLOR.RED:``                        ` `                        ``# Left Left``                        ``if` `sibling.isOnLeft():``                            ``sibling.left.color ``=` `sibling.color``                            ``sibling.color ``=` `parent.color``                            ``self``.rightRotate(parent)``                        ` `                        ``# Right Left``                        ``else``:``                            ``sibling.left.color ``=` `parent.color``                            ``self``.rightRotate(sibling)``                            ``self``.leftRotate(parent)``                    ``else``:``                        ` `                        ``# Left Right``                        ``if` `sibling.isOnLeft():``                            ``sibling.right.color ``=` `parent.color``                            ``self``.leftRotate(sibling)``                            ``self``.rightRotate(parent)``                        ` `                        ``# Right Right``                        ``else``:``                            ``sibling.right.color ``=` `sibling.color``                            ``sibling.color ``=` `parent.color``                            ``self``.leftRotate(parent)``                ` `                ``# 2 black children``                ``else``:``                    ``sibling.color ``=` `COLOR.RED``                    ``if` `parent.color ``=``=` `COLOR.BLACK:``                        ``self``.fixDoubleBlack(parent)``                    ``else``:``                        ``parent.color ``=` `COLOR.BLACK``    ` `    ``# Prints the level order traversal of the tree starting from the given node``    ``def` `levelOrder(``self``, x):``        ``if` `x ``is` `None``:``            ``return` `        ``q ``=` `Queue()``        ``q.put(x)` `        ``while` `not` `q.empty():``            ``curr ``=` `q.get()``            ``print``(curr.val, end``=``" "``)` `            ``if` `curr.left ``is` `not` `None``:``                ``q.put(curr.left)``            ``if` `curr.right ``is` `not` `None``:``                ``q.put(curr.right)``    ` `    ``# Prints the in-order traversal of the tree starting from the given node``    ``def` `inorder(``self``, x):``        ``if` `x ``is` `None``:``            ``return``        ``self``.inorder(x.left)``        ``print``(x.val, end``=``" "``)``        ``self``.inorder(x.right)` `    ``def` `getRoot(``self``):``        ``return` `self``.root``    ` `    ``# Searches for a given value in the tree and returns the node if found``    ``# Otherwise, returns the last node encountered while traversing``    ``def` `search(``self``, n):``        ``temp ``=` `self``.root``        ``while` `temp ``is` `not` `None``:``            ``if` `n < temp.val:``                ``if` `temp.left ``is` `None``:``                    ``break``                ``else``:``                    ``temp ``=` `temp.left``            ``elif` `n ``=``=` `temp.val:``                ``break``            ``else``:``                ``if` `temp.right ``is` `None``:``                    ``break``                ``else``:``                    ``temp ``=` `temp.right` `        ``return` `temp``    ` `    ``# Inserts the given value into the tree``    ``def` `insert(``self``, n):``        ``newNode ``=` `Node(n)``        ` `        ``# When the tree is empty``        ``if` `self``.root ``is` `None``:``            ``newNode.color ``=` `COLOR.BLACK``            ``self``.root ``=` `newNode``        ``else``:``            ``temp ``=` `self``.search(n)``            ` `            ``# Value already exists, return``            ``if` `temp.val ``=``=` `n:``                ``return``            ` `            ``# Connect the new node to the correct node``            ``newNode.parent ``=` `temp` `            ``if` `n < temp.val:``                ``temp.left ``=` `newNode``            ``else``:``                ``temp.right ``=` `newNode``            ` `            ``# Fix red-red violation if it exists``            ``self``.fixRedRed(newNode)``    ` `    ``# Deletes the node with the given value from the tree``    ``def` `deleteByVal(``self``, n):``        ` `        ``# Tree is empty``        ``if` `self``.root ``is` `None``:``            ``return` `        ``v ``=` `self``.search(n)` `        ``if` `v.val !``=` `n:``            ``print``(f``"No node found to delete with value: {n}"``)``            ``return` `        ``self``.deleteNode(v)``    ` `    ``# Prints the in-order traversal of the tree``    ``def` `printInOrder(``self``):``        ``print``(``"Inorder:"``)``        ``if` `self``.root ``is` `None``:``            ``print``(``"Tree is empty"``)``        ``else``:``            ``self``.inorder(``self``.root)``        ``print``()``    ` `    ``# Prints the level order traversal of the tree``    ``def` `printLevelOrder(``self``):``        ``print``(``"Level order:"``)``        ``if` `self``.root ``is` `None``:``            ``print``(``"Tree is empty"``)``        ``else``:``            ``self``.levelOrder(``self``.root)``        ``print``()` `# Test the RBTree``tree ``=` `RBTree()` `tree.insert(``7``)``tree.insert(``3``)``tree.insert(``18``)``tree.insert(``10``)``tree.insert(``22``)``tree.insert(``8``)``tree.insert(``11``)``tree.insert(``26``)``tree.insert(``2``)``tree.insert(``6``)``tree.insert(``13``)` `tree.printInOrder()``tree.printLevelOrder()` `print``(``"Deleting 18, 11, 3, 10, 22"``)` `tree.deleteByVal(``18``)``tree.deleteByVal(``11``)``tree.deleteByVal(``3``)``tree.deleteByVal(``10``)``tree.deleteByVal(``22``)` `tree.printInOrder()``tree.printLevelOrder()` `# This code is contributed by Susobhan Akhuli`

C#

 `// C# program for the above approach``using` `System;``using` `System.Collections.Generic;` `enum` `COLOR { RED, BLACK }``;` `class` `Node {``    ``public` `int` `val;``    ``public` `COLOR color;``    ``public` `Node left, right, parent;` `    ``public` `Node(``int` `val)``    ``{``        ``this``.val = val;``        ``parent = left = right = ``null``;` `        ``// Node is created during insertion``        ``// Node is red at insertion``        ``color = COLOR.RED;``    ``}` `    ``// Returns pointer to uncle``    ``public` `Node Uncle()``    ``{``        ``// If no parent or grandparent, then no uncle``        ``if` `(parent == ``null` `|| parent.parent == ``null``)``            ``return` `null``;` `        ``if` `(parent.IsOnLeft())``            ``// Uncle on right``            ``return` `parent.parent.right;``        ``else``            ``// Uncle on left``            ``return` `parent.parent.left;``    ``}` `    ``// Check if node is left child of parent``    ``public` `bool` `IsOnLeft() { ``return` `this` `== parent.left; }` `    ``// Returns pointer to sibling``    ``public` `Node Sibling()``    ``{``        ``// Sibling null if no parent``        ``if` `(parent == ``null``)``            ``return` `null``;` `        ``if` `(IsOnLeft())``            ``return` `parent.right;` `        ``return` `parent.left;``    ``}` `    ``// Moves node down and moves given node in its place``    ``public` `void` `MoveDown(Node nParent)``    ``{``        ``if` `(parent != ``null``) {``            ``if` `(IsOnLeft())``                ``parent.left = nParent;``            ``else``                ``parent.right = nParent;``        ``}``        ``nParent.parent = parent;``        ``parent = nParent;``    ``}` `    ``public` `bool` `HasRedChild()``    ``{``        ``return` `(left != ``null` `&& left.color == COLOR.RED)``            ``|| (right != ``null` `&& right.color == COLOR.RED);``    ``}``}` `class` `RBTree {``    ``Node root;` `    ``// Left rotates the given node``    ``void` `LeftRotate(Node x)``    ``{``        ``// New parent will be node's right child``        ``Node nParent = x.right;` `        ``// Update root if current node is root``        ``if` `(x == root)``            ``root = nParent;` `        ``x.MoveDown(nParent);` `        ``// Connect x with new parent's left element``        ``x.right = nParent.left;` `        ``// Connect new parent's left element with node``        ``// If it is not null``        ``if` `(nParent.left != ``null``)``            ``nParent.left.parent = x;` `        ``// Connect new parent with x``        ``nParent.left = x;``    ``}` `    ``void` `RightRotate(Node x)``    ``{``        ``// New parent will be node's left child``        ``Node nParent = x.left;` `        ``// Update root if current node is root``        ``if` `(x == root)``            ``root = nParent;` `        ``x.MoveDown(nParent);` `        ``// Connect x with new parent's right element``        ``x.left = nParent.right;` `        ``// Connect new parent's right element with node``        ``// If it is not null``        ``if` `(nParent.right != ``null``)``            ``nParent.right.parent = x;` `        ``// Connect new parent with x``        ``nParent.right = x;``    ``}` `    ``void` `SwapColors(Node x1, Node x2)``    ``{``        ``COLOR temp = x1.color;``        ``x1.color = x2.color;``        ``x2.color = temp;``    ``}` `    ``void` `SwapValues(Node u, Node v)``    ``{``        ``int` `temp = u.val;``        ``u.val = v.val;``        ``v.val = temp;``    ``}` `    ``// Fix red red at given node``    ``void` `FixRedRed(Node x)``    ``{``        ``// If x is root, color it black and return``        ``if` `(x == root) {``            ``x.color = COLOR.BLACK;``            ``return``;``        ``}` `        ``// Initialize parent, grandparent, uncle``        ``Node parent = x.parent, grandparent = parent.parent,``             ``uncle = x.Uncle();` `        ``if` `(parent.color != COLOR.BLACK) {``            ``if` `(uncle != ``null` `&& uncle.color == COLOR.RED) {``                ``// Uncle red, perform recoloring and recurse``                ``parent.color = COLOR.BLACK;``                ``uncle.color = COLOR.BLACK;``                ``grandparent.color = COLOR.RED;``                ``FixRedRed(grandparent);``            ``}``            ``else` `{``                ``// Else perform LR, LL, RL, RR``                ``if` `(parent.IsOnLeft()) {``                    ``if` `(x.IsOnLeft()) {``                        ``// For left right``                        ``SwapColors(parent, grandparent);``                    ``}``                    ``else` `{``                        ``LeftRotate(parent);``                        ``SwapColors(x, grandparent);``                    ``}``                    ``// For left left and left right``                    ``RightRotate(grandparent);``                ``}``                ``else` `{``                    ``if` `(x.IsOnLeft()) {``                        ``// For right left``                        ``RightRotate(parent);``                        ``SwapColors(x, grandparent);``                    ``}``                    ``else` `{``                        ``SwapColors(parent, grandparent);``                    ``}` `                    ``// For right right and right left``                    ``LeftRotate(grandparent);``                ``}``            ``}``        ``}``    ``}` `    ``// Find node that does not have a left child``    ``// in the subtree of the given node``    ``Node Successor(Node x)``    ``{``        ``Node temp = x;``        ``while` `(temp.left != ``null``)``            ``temp = temp.left;``        ``return` `temp;``    ``}` `    ``// Find node that replaces a deleted node in BST``    ``Node BSTreplace(Node x)``    ``{``        ``// When node has 2 children``        ``if` `(x.left != ``null` `&& x.right != ``null``)``            ``return` `Successor(x.right);` `        ``// When leaf``        ``if` `(x.left == ``null` `&& x.right == ``null``)``            ``return` `null``;` `        ``// When single child``        ``return` `x.left != ``null` `? x.left : x.right;``    ``}` `    ``// Deletes the given node``    ``void` `DeleteNode(Node v)``    ``{``        ``Node u = BSTreplace(v);` `        ``// True when u and v are both black``        ``bool` `uvBlack``            ``= ((u == ``null` `|| u.color == COLOR.BLACK)``               ``&& (v.color == COLOR.BLACK));``        ``Node parent = v.parent;` `        ``if` `(u == ``null``) {``            ``// u is NULL therefore v is leaf``            ``if` `(v == root) {``                ``// v is root, making root null``                ``root = ``null``;``            ``}``            ``else` `{``                ``if` `(uvBlack) {``                    ``// u and v both black``                    ``// v is leaf, fix double black at v``                    ``FixDoubleBlack(v);``                ``}``                ``else` `{``                    ``// u or v red, color u black``                    ``if` `(v.Sibling() != ``null``)``                        ``// Sibling is not null, make it red``                        ``v.Sibling().color = COLOR.RED;``                ``}` `                ``// Delete v from the tree``                ``if` `(v.IsOnLeft()) {``                    ``parent.left = ``null``;``                ``}``                ``else` `{``                    ``parent.right = ``null``;``                ``}``            ``}``            ``return``;``        ``}` `        ``if` `(v.left == ``null` `|| v.right == ``null``) {``            ``// v has 1 child``            ``if` `(v == root) {``                ``// v is root, assign the value of u to v,``                ``// and delete u``                ``v.val = u.val;``                ``v.left = v.right = ``null``;``                ``DeleteNode(u);``            ``}``            ``else` `{``                ``// Detach v from tree and move u up``                ``if` `(v.IsOnLeft()) {``                    ``parent.left = u;``                ``}``                ``else` `{``                    ``parent.right = u;``                ``}``                ``u.parent = parent;` `                ``if` `(uvBlack) {``                    ``// u and v both black, fix double black``                    ``// at u``                    ``FixDoubleBlack(u);``                ``}``                ``else` `{``                    ``// u or v red, color u black``                    ``u.color = COLOR.BLACK;``                ``}``            ``}``            ``return``;``        ``}` `        ``// v has 2 children, swap values with successor and``        ``// recurse``        ``SwapValues(u, v);``        ``DeleteNode(u);``    ``}` `    ``void` `FixDoubleBlack(Node x)``    ``{``        ``// Reached root``        ``if` `(x == root)``            ``return``;` `        ``Node sibling = x.Sibling(), parent = x.parent;` `        ``if` `(sibling == ``null``) {``            ``// No sibling, double black pushed up``            ``FixDoubleBlack(parent);``        ``}``        ``else` `{``            ``if` `(sibling.color == COLOR.RED) {``                ``// Sibling red``                ``parent.color = COLOR.RED;``                ``sibling.color = COLOR.BLACK;``                ``if` `(sibling.IsOnLeft()) {``                    ``// Left case``                    ``RightRotate(parent);``                ``}``                ``else` `{``                    ``// Right case``                    ``LeftRotate(parent);``                ``}``                ``FixDoubleBlack(x);``            ``}``            ``else` `{``                ``// Sibling black``                ``if` `(sibling.HasRedChild()) {``                    ``// At least 1 red children``                    ``if` `(sibling.left != ``null``                        ``&& sibling.left.color``                               ``== COLOR.RED) {``                        ``if` `(sibling.IsOnLeft()) {``                            ``// Left left``                            ``sibling.left.color``                                ``= sibling.color;``                            ``sibling.color = parent.color;``                            ``RightRotate(parent);``                        ``}``                        ``else` `{``                            ``// Right left``                            ``sibling.left.color``                                ``= parent.color;``                            ``RightRotate(sibling);``                            ``LeftRotate(parent);``                        ``}``                    ``}``                    ``else` `{``                        ``if` `(sibling.IsOnLeft()) {``                            ``// Left right``                            ``sibling.right.color``                                ``= parent.color;``                            ``LeftRotate(sibling);``                            ``RightRotate(parent);``                        ``}``                        ``else` `{``                            ``// Right right``                            ``sibling.right.color``                                ``= sibling.color;``                            ``sibling.color = parent.color;``                            ``LeftRotate(parent);``                        ``}``                    ``}``                    ``parent.color = COLOR.BLACK;``                ``}``                ``else` `{``                    ``// 2 black children``                    ``sibling.color = COLOR.RED;``                    ``if` `(parent.color == COLOR.BLACK)``                        ``FixDoubleBlack(parent);``                    ``else``                        ``parent.color = COLOR.BLACK;``                ``}``            ``}``        ``}``    ``}` `    ``// Prints level order for given node``    ``void` `LevelOrder(Node x)``    ``{``        ``if` `(x == ``null``)``            ``return``;` `        ``// Queue for level order``        ``Queue q = ``new` `Queue();``        ``Node curr;` `        ``// Push x``        ``q.Enqueue(x);` `        ``while` `(q.Count > 0) {``            ``// While q is not empty``            ``// Dequeue``            ``curr = q.Dequeue();` `            ``// Print node value``            ``Console.Write(curr.val + ``" "``);` `            ``// Push children to queue``            ``if` `(curr.left != ``null``)``                ``q.Enqueue(curr.left);``            ``if` `(curr.right != ``null``)``                ``q.Enqueue(curr.right);``        ``}``    ``}` `    ``// Prints inorder recursively``    ``void` `Inorder(Node x)``    ``{``        ``if` `(x == ``null``)``            ``return``;``        ``Inorder(x.left);``        ``Console.Write(x.val + ``" "``);``        ``Inorder(x.right);``    ``}` `    ``public` `Node GetRoot() { ``return` `root; }` `    ``// Searches for given value``    ``// If found, returns the node (used for delete)``    ``// Else returns the last node while traversing (used in``    ``// insert)``    ``Node Search(``int` `n)``    ``{``        ``Node temp = root;``        ``while` `(temp != ``null``) {``            ``if` `(n < temp.val) {``                ``if` `(temp.left == ``null``)``                    ``break``;``                ``else``                    ``temp = temp.left;``            ``}``            ``else` `if` `(n == temp.val) {``                ``break``;``            ``}``            ``else` `{``                ``if` `(temp.right == ``null``)``                    ``break``;``                ``else``                    ``temp = temp.right;``            ``}``        ``}` `        ``return` `temp;``    ``}` `    ``// Inserts the given value to tree``    ``public` `void` `Insert(``int` `n)``    ``{``        ``Node newNode = ``new` `Node(n);``        ``if` `(root == ``null``) {``            ``// When root is null``            ``// Simply insert value at root``            ``newNode.color = COLOR.BLACK;``            ``root = newNode;``        ``}``        ``else` `{``            ``Node temp = Search(n);` `            ``if` `(temp.val == n) {``                ``// Return if value already exists``                ``return``;``            ``}` `            ``// If value is not found, search returns the``            ``// node where the value is to be inserted` `            ``// Connect new node to correct node``            ``newNode.parent = temp;` `            ``if` `(n < temp.val)``                ``temp.left = newNode;``            ``else``                ``temp.right = newNode;` `            ``// Fix red-red violation if exists``            ``FixRedRed(newNode);``        ``}``    ``}` `    ``// Utility function that deletes the node with given``    ``// value``    ``public` `void` `DeleteByVal(``int` `n)``    ``{``        ``if` `(root == ``null``)``            ``// Tree is empty``            ``return``;` `        ``Node v = Search(n);` `        ``if` `(v.val != n) {``            ``Console.WriteLine(``                ``"No node found to delete with value:"` `+ n);``            ``return``;``        ``}` `        ``DeleteNode(v);``    ``}` `    ``// Prints inorder of the tree``    ``public` `void` `PrintInOrder()``    ``{``        ``Console.WriteLine(``"Inorder: "``);``        ``if` `(root == ``null``)``            ``Console.WriteLine(``"Tree is empty"``);``        ``else``            ``Inorder(root);``        ``Console.WriteLine();``    ``}` `    ``// Prints level order of the tree``    ``public` `void` `PrintLevelOrder()``    ``{``        ``Console.WriteLine(``"Level order: "``);``        ``if` `(root == ``null``)``            ``Console.WriteLine(``"Tree is empty"``);``        ``else``            ``LevelOrder(root);``        ``Console.WriteLine();``    ``}``}` `public` `class` `GFG {``    ``static` `void` `Main()``    ``{``        ``RBTree tree = ``new` `RBTree();` `        ``tree.Insert(7);``        ``tree.Insert(3);``        ``tree.Insert(18);``        ``tree.Insert(10);``        ``tree.Insert(22);``        ``tree.Insert(8);``        ``tree.Insert(11);``        ``tree.Insert(26);``        ``tree.Insert(2);``        ``tree.Insert(6);``        ``tree.Insert(13);` `        ``tree.PrintInOrder();``        ``tree.PrintLevelOrder();` `        ``Console.WriteLine(``"\nDeleting 18, 11, 3, 10, 22\n"``);` `        ``tree.DeleteByVal(18);``        ``tree.DeleteByVal(11);``        ``tree.DeleteByVal(3);``        ``tree.DeleteByVal(10);``        ``tree.DeleteByVal(22);` `        ``tree.PrintInOrder();``        ``tree.PrintLevelOrder();``    ``}``}` `// This code is contributed by Susobhan Akhuli`

Javascript

 ``

Output:Â

`Inorder: 2 3 6 7 8 10 11 13 18 22 26 Level order: 10 7 18 3 8 11 22 2 6 13 26 Deleting 18, 11, 3, 10, 22Inorder: 2 6 7 8 13 26 Level order: 13 7 26 6 8 2 `

Previous
Next