Ridwanul_Haque

RBT

Oct 23rd, 2020
99
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 9.29 KB | None | 0 0
  1.  
  2. // Red Black Tree implementation in C++
  3. // Author: Algorithm Tutor
  4. // Tutorial URL: https://algorithmtutor.com/Data-Structures/Tree/Red-Black-Trees/
  5.  
  6. #include <iostream>
  7.  
  8. using namespace std;
  9.  
  10. // data structure that represents a node in the tree
  11. struct Node {
  12.     int data; // holds the key
  13.     Node *parent; // pointer to the parent
  14.     Node *left; // pointer to left child
  15.     Node *right; // pointer to right child
  16.     int color; // 1 -> Red, 0 -> Black
  17. };
  18.  
  19. typedef Node *NodePtr;
  20.  
  21. // class RBTree implements the operations in Red Black Tree
  22. class RBTree {
  23. private:
  24.     NodePtr root;
  25.     NodePtr TNULL;
  26.  
  27.     // initializes the nodes with appropirate values
  28.     // all the pointers are set to point to the null pointer
  29.     void initializeNULLNode(NodePtr node, NodePtr parent) {
  30.         node->data = 0;
  31.         node->parent = parent;
  32.         node->left = nullptr;
  33.         node->right = nullptr;
  34.         node->color = 0;
  35.     }
  36.  
  37.  
  38.     NodePtr searchTreeHelper(NodePtr node, int key) {
  39.         if (node == TNULL || key == node->data) {
  40.             return node;
  41.         }
  42.  
  43.         if (key < node->data) {
  44.             return searchTreeHelper(node->left, key);
  45.         }
  46.         return searchTreeHelper(node->right, key);
  47.     }
  48.  
  49.     // fix the rb tree modified by the delete operation
  50.     void fixDelete(NodePtr x) {
  51.         NodePtr s;
  52.         while (x != root && x->color == 0) {
  53.             if (x == x->parent->left) {
  54.                 s = x->parent->right;
  55.                 if (s->color == 1) {
  56.                     // case 3.1
  57.                     s->color = 0;
  58.                     x->parent->color = 1;
  59.                     leftRotate(x->parent);
  60.                     s = x->parent->right;
  61.                 }
  62.  
  63.                 if (s->left->color == 0 && s->right->color == 0) {
  64.                     // case 3.2
  65.                     s->color = 1;
  66.                     x = x->parent;
  67.                 } else {
  68.                     if (s->right->color == 0) {
  69.                         // case 3.3
  70.                         s->left->color = 0;
  71.                         s->color = 1;
  72.                         rightRotate(s);
  73.                         s = x->parent->right;
  74.                     }
  75.  
  76.                     // case 3.4
  77.                     s->color = x->parent->color;
  78.                     x->parent->color = 0;
  79.                     s->right->color = 0;
  80.                     leftRotate(x->parent);
  81.                     x = root;
  82.                 }
  83.             } else {
  84.                 s = x->parent->left;
  85.                 if (s->color == 1) {
  86.                     // case 3.1
  87.                     s->color = 0;
  88.                     x->parent->color = 1;
  89.                     rightRotate(x->parent);
  90.                     s = x->parent->left;
  91.                 }
  92.  
  93.                 if (s->right->color == 0 && s->right->color == 0) {
  94.                     // case 3.2
  95.                     s->color = 1;
  96.                     x = x->parent;
  97.                 } else {
  98.                     if (s->left->color == 0) {
  99.                         // case 3.3
  100.                         s->right->color = 0;
  101.                         s->color = 1;
  102.                         leftRotate(s);
  103.                         s = x->parent->left;
  104.                     }
  105.  
  106.                     // case 3.4
  107.                     s->color = x->parent->color;
  108.                     x->parent->color = 0;
  109.                     s->left->color = 0;
  110.                     rightRotate(x->parent);
  111.                     x = root;
  112.                 }
  113.             }
  114.         }
  115.         x->color = 0;
  116.     }
  117.  
  118.  
  119.     void rbTransplant(NodePtr u, NodePtr v){
  120.         if (u->parent == nullptr) {
  121.             root = v;
  122.         } else if (u == u->parent->left){
  123.             u->parent->left = v;
  124.         } else {
  125.             u->parent->right = v;
  126.         }
  127.         v->parent = u->parent;
  128.     }
  129.  
  130.     void deleteNodeHelper(NodePtr node, int key) {
  131.         // find the node containing key
  132.         NodePtr z = TNULL;
  133.         NodePtr x, y;
  134.         while (node != TNULL){
  135.             if (node->data == key) {
  136.                 z = node;
  137.             }
  138.  
  139.             if (node->data <= key) {
  140.                 node = node->right;
  141.             } else {
  142.                 node = node->left;
  143.             }
  144.         }
  145.  
  146.         if (z == TNULL) {
  147.  
  148.             return;
  149.         }
  150.  
  151.         y = z;
  152.         int y_original_color = y->color;
  153.         if (z->left == TNULL) {
  154.             x = z->right;
  155.             rbTransplant(z, z->right);
  156.         } else if (z->right == TNULL) {
  157.             x = z->left;
  158.             rbTransplant(z, z->left);
  159.         } else {
  160.             y = minimum(z->right);
  161.             y_original_color = y->color;
  162.             x = y->right;
  163.             if (y->parent == z) {
  164.                 x->parent = y;
  165.             } else {
  166.                 rbTransplant(y, y->right);
  167.                 y->right = z->right;
  168.                 y->right->parent = y;
  169.             }
  170.  
  171.             rbTransplant(z, y);
  172.             y->left = z->left;
  173.             y->left->parent = y;
  174.             y->color = z->color;
  175.         }
  176.         delete z;
  177.         if (y_original_color == 0){
  178.             fixDelete(x);
  179.         }
  180.     }
  181.  
  182.     // fix the red-black tree
  183.     void fixInsert(NodePtr k){
  184.         NodePtr u;
  185.         while (k->parent->color == 1) {
  186.             if (k->parent == k->parent->parent->right) {
  187.                 u = k->parent->parent->left; // uncle
  188.                 if (u->color == 1) {
  189.                     // case 3.1
  190.                     u->color = 0;
  191.                     k->parent->color = 0;
  192.                     k->parent->parent->color = 1;
  193.                     k = k->parent->parent;
  194.                 } else {
  195.                     if (k == k->parent->left) {
  196.                         // case 3.2.2
  197.                         k = k->parent;
  198.                         rightRotate(k);
  199.                     }
  200.                     // case 3.2.1
  201.                     k->parent->color = 0;
  202.                     k->parent->parent->color = 1;
  203.                     leftRotate(k->parent->parent);
  204.                 }
  205.             } else {
  206.                 u = k->parent->parent->right; // uncle
  207.  
  208.                 if (u->color == 1) {
  209.                     // mirror case 3.1
  210.                     u->color = 0;
  211.                     k->parent->color = 0;
  212.                     k->parent->parent->color = 1;
  213.                     k = k->parent->parent;
  214.                 } else {
  215.                     if (k == k->parent->right) {
  216.                         // mirror case 3.2.2
  217.                         k = k->parent;
  218.                         leftRotate(k);
  219.                     }
  220.                     // mirror case 3.2.1
  221.                     k->parent->color = 0;
  222.                     k->parent->parent->color = 1;
  223.                     rightRotate(k->parent->parent);
  224.                 }
  225.             }
  226.             if (k == root) {
  227.                 break;
  228.             }
  229.         }
  230.         root->color = 0;
  231.     }
  232.  
  233.     void printHelper(NodePtr root, string indent, bool last) {
  234.         // print the tree structure on the screen
  235.         if (root != TNULL) {
  236.            cout<<indent;
  237.            if (last) {
  238.               cout<<"R----";
  239.               indent += "     ";
  240.            } else {
  241.               cout<<"L----";
  242.               indent += "|    ";
  243.            }
  244.  
  245.            string sColor = root->color?"RED":"BLACK";
  246.            cout<<root->data<<"("<<sColor<<")"<<endl;
  247.            printHelper(root->left, indent, false);
  248.            printHelper(root->right, indent, true);
  249.         }
  250.         // cout<<root->left->data<<endl;
  251.     }
  252.  
  253. public:
  254.     RBTree() {
  255.         TNULL = new Node;
  256.         TNULL->color = 0;
  257.         TNULL->left = nullptr;
  258.         TNULL->right = nullptr;
  259.         root = TNULL;
  260.     }
  261.  
  262.  
  263.  
  264.  
  265.     // find the node with the minimum key
  266.     NodePtr minimum(NodePtr node) {
  267.         while (node->left != TNULL) {
  268.             node = node->left;
  269.         }
  270.         return node;
  271.     }
  272.  
  273.     // find the node with the maximum key
  274.     NodePtr maximum(NodePtr node) {
  275.         while (node->right != TNULL) {
  276.             node = node->right;
  277.         }
  278.         return node;
  279.     }
  280.  
  281.     // find the successor of a given node
  282. //  NodePtr successor(NodePtr x) {
  283. //      // if the right subtree is not null,
  284. //      // the successor is the leftmost node in the
  285. //      // right subtree
  286. //      if (x->right != TNULL) {
  287. //          return minimum(x->right);
  288. //      }
  289. //
  290. //      // else it is the lowest ancestor of x whose
  291. //      // left child is also an ancestor of x.
  292. //      NodePtr y = x->parent;
  293. //      while (y != TNULL && x == y->right) {
  294. //          x = y;
  295. //          y = y->parent;
  296. //      }
  297. //      return y;
  298. //  }
  299.  
  300.     // find the predecessor of a given node
  301. //  NodePtr predecessor(NodePtr x) {
  302. //      // if the left subtree is not null,
  303. //      // the predecessor is the rightmost node in the
  304. //      // left subtree
  305. //      if (x->left != TNULL) {
  306. //          return maximum(x->left);
  307. //      }
  308. //
  309. //      NodePtr y = x->parent;
  310. //      while (y != TNULL && x == y->left) {
  311. //          x = y;
  312. //          y = y->parent;
  313. //      }
  314. //
  315. //      return y;
  316. //  }
  317.  
  318.     // rotate left at node x
  319.     void leftRotate(NodePtr x) {
  320.         NodePtr y = x->right;
  321.         x->right = y->left;
  322.         if (y->left != TNULL) {
  323.             y->left->parent = x;
  324.         }
  325.         y->parent = x->parent;
  326.         if (x->parent == nullptr) {
  327.             this->root = y;
  328.         } else if (x == x->parent->left) {
  329.             x->parent->left = y;
  330.         } else {
  331.             x->parent->right = y;
  332.         }
  333.         y->left = x;
  334.         x->parent = y;
  335.     }
  336.  
  337.     // rotate right at node x
  338.     void rightRotate(NodePtr x) {
  339.         NodePtr y = x->left;
  340.         x->left = y->right;
  341.         if (y->right != TNULL) {
  342.             y->right->parent = x;
  343.         }
  344.         y->parent = x->parent;
  345.         if (x->parent == nullptr) {
  346.             this->root = y;
  347.         } else if (x == x->parent->right) {
  348.             x->parent->right = y;
  349.         } else {
  350.             x->parent->left = y;
  351.         }
  352.         y->right = x;
  353.         x->parent = y;
  354.     }
  355.  
  356.     // insert the key to the tree in its appropriate position
  357.     // and fix the tree
  358.     void insert(int key) {
  359.         // Ordinary Binary Search Insertion
  360.         NodePtr node = new Node;
  361.         node->parent = nullptr;
  362.         node->data = key;
  363.         node->left = TNULL;
  364.         node->right = TNULL;
  365.         node->color = 1; // new node must be red
  366.  
  367.         NodePtr y = nullptr;
  368.         NodePtr x = this->root;
  369.  
  370.         while (x != TNULL) {
  371.             y = x;
  372.             if (node->data < x->data) {
  373.                 x = x->left;
  374.             } else {
  375.                 x = x->right;
  376.             }
  377.         }
  378.  
  379.         // y is parent of x
  380.         node->parent = y;
  381.         if (y == nullptr) {
  382.             root = node;
  383.         } else if (node->data < y->data) {
  384.             y->left = node;
  385.         } else {
  386.             y->right = node;
  387.         }
  388.  
  389.         // if new node is a root node, simply return
  390.         if (node->parent == nullptr){
  391.             node->color = 0;
  392.             return;
  393.         }
  394.  
  395.         // if the grandparent is null, simply return
  396.         if (node->parent->parent == nullptr) {
  397.             return;
  398.         }
  399.  
  400.         // Fix the tree
  401.         fixInsert(node);
  402.     }
  403.  
  404.     NodePtr getRoot(){
  405.         return this->root;
  406.     }
  407.  
  408.     // delete the node from the tree
  409.     void deleteNode(int data) {
  410.         deleteNodeHelper(this->root, data);
  411.     }
  412.  
  413.     // print the tree structure on the screen
  414.     void prettyPrint() {
  415.         if (root) {
  416.             printHelper(this->root, "", true);
  417.         }
  418.     }
  419.  
  420.     // search the tree for the key k
  421.     // and return the corresponding node
  422.     NodePtr searchTree(int k) {
  423.         return searchTreeHelper(this->root, k);
  424.     }
  425.  
  426. };
  427.  
  428.  
  429.  
  430. int main() {
  431.     Node *node;
  432.     RBTree bst;
  433.     bst.insert(1);
  434.     bst.insert(3);
  435.     bst.insert(2);
  436.     int n = 2;
  437.     node = bst.searchTree(2);
  438.     if(n!=node->data)
  439.     {
  440.         bst.insert(2);
  441.     }
  442.     bst.insert(5);
  443.     bst.insert(7);
  444.     bst.insert(4);
  445.     bst.insert(6);
  446.     bst.insert(8);
  447.     bst.insert(10);
  448.     bst.deleteNode(7);
  449.     bst.deleteNode(1);
  450. //  bst.deleteNode(8);
  451.  
  452.  
  453.  
  454.     bst.prettyPrint();
  455.  
  456.  
  457.     return 0;
  458. }
  459.  
Add Comment
Please, Sign In to add comment