static void insert_case3(L_RBTREE *t, node *n) { if (node_color(uncle(n)) == L_RED_NODE) { n->parent->color = L_BLACK_NODE; uncle(n)->color = L_BLACK_NODE; grandparent(n)->color = L_RED_NODE; insert_case1(t, grandparent(n)); } else { insert_case4(t, n); } }
void insert_case3(rbtree t, node n) { if (node_color(uncle(n)) == RED) { n->parent->color = BLACK; uncle(n)->color = BLACK; grandparent(n)->color = RED; insert_case1(t, grandparent(n)); } else { insert_case4(t, n); } }
void insertCase3(rbTree tree, rbTreeNode node) { if (nodeColor(uncle(node)) == 1) { //RED node->parent->color = 0; //BLACK uncle(node)->color = 0; //BLACK grandparent(node)->color = 1; //RED insertCase1(tree, grandparent(node)); } else { insertCase4(tree, node); } }
void restore_properties(Node *node) { if (parent(node) == nullptr) // Cenário A: node é a raiz node->color = Node::BLACK; else if (parent(node)->color == Node::BLACK) // Cenário B return; else if (uncle(node) and uncle(node)->color == Node::RED) { // Cenário C: pai e tio vermelhos parent(node)->color = Node::BLACK; uncle(node)->color = Node::BLACK; grandparent(node)->color = Node::RED; // Como o pai é vermelho, o avô não é nulo restore_properties(grandparent(node)); } else { // Cenário D: pai vermelho, tio preto auto C = node; auto P = parent(node); auto G = grandparent(node); if (C == P->right and P == G->left) { rotate_left(G, P, C); P = C; } else if (node == P->left and P == G->right) { rotate_right(G, P, C); P = C; } C = P; P = G; G = parent(P); if (C == P->left) rotate_right(G, P, C); else rotate_left(G, P, C); // Corner case: após a rotação C é a nova raiz if (G == nullptr) root = C; C->color = Node::BLACK; P->color = Node::RED; } }
void insert(node *head, node *n) { node *u = NULL; /* * When !head */ if (!head) { n->color = BLACK; head = n; return; } if (n->parent == BLACK) { } else if (n->parent == RED) { } u = uncle(n); if (u && u->color == RED) { } else if (u && u->color == BLACK) { } else { /* * No uncle */ } }
void rb_tree_insert_repair(tree_t *tree, node_t *n) { // przypadek 1: korzeń if (is_nil(parent(n))) { n->color = BLACK; return; } // przypadek 2: rodzic czarny if (parent(n)->color == BLACK) return; // przypadek 3: rodzic czerwony; wuj czerwony; if (!is_nil(uncle(n)) && uncle(n)->color == RED) { parent(n)->color = BLACK; uncle(n)->color = BLACK; grandparent(n)->color = RED; rb_tree_insert_repair(tree, grandparent(n)); } else // przypadek 4: rodzic czerwony; wuj czarny; { if (is_right_child(n) && is_left_child(parent(n))) { node_rotate_left(tree, parent(n)); n = n->left; } else if (is_left_child(n) && is_right_child(parent(n))) { node_rotate_right(tree, parent(n)); n = n->right; } // case 5: wuj czarny; nowy, rodzic, dziadek na prostej; nowy i rodzic czerwoni; parent(n)->color = BLACK; grandparent(n)->color = RED; if (is_left_child(n) && is_left_child(parent(n))) node_rotate_right(tree, grandparent(n)); else node_rotate_left(tree, grandparent(n)); } }
/* * Insert Fixup * */ void rb_insert(struct rb_t *tree,struct rb_node_t *node) { tree_insert(tree,node); printf("root "); tree->print(tree->root); while((node->parent) && (node->parent->colour == RED)) { if(node->parent == node->parent->parent->left) { struct rb_node_t *y = uncle(node); if(y && (y->colour == RED)) { node->parent->colour = BLACK; y->colour = BLACK; node->parent->parent->colour = RED; node = node->parent->parent; } else { if(node == node->parent->right) { node = node->parent; left_rotate(tree,node); } node->parent->colour = BLACK; node->parent->parent->colour = RED; right_rotate(tree,node->parent->parent); } } else { struct rb_node_t *y = uncle(node); if(y && (y->colour == RED)) { node->parent->colour = BLACK; y->colour = BLACK; node->parent->parent->colour = RED; node = node->parent->parent; } else { if(node == node->parent->left) { node = node->parent; right_rotate(tree,node); } node->parent->colour = BLACK; node->parent->parent->colour = RED; left_rotate(tree,node->parent->parent); } } } tree->root->colour = BLACK; }
void insert_case3(rb_node* n, rb_tree* tree) { rb_node* u = uncle(n), *g; if ((u != NULL) && (u->color == RED)) { n->parent->color = BLACK; u->color = BLACK; g = grandparent(n); g->color = RED; insert_case1(g, tree); } else { insert_case4(n, tree); } }
//Caso 3 - Si el nodo insertado tiene un padre y un "tio" rojos, estos pueden ser pintados negros, y pintando el abuelo rojo, esto mantiene // la propiedad de el numero de nodos negros en los arboles, pero ahora el abuelo puede estar violando otras propiedades. void RBTree::fixup_case3(RBNode* n) { RBNode* tio = uncle(n); RBNode* abuelo = grandparent(n); if( !(tio->getCentinel()) && ( tio->getColor() == ROJO ) ){ n->father->setColor(NEGRO); tio->setColor(NEGRO); abuelo->setColor(ROJO); fixup_case1(abuelo); } else{ fixup_case4(n); } }
static void rb_tree_insert_case3(rb_node_t *node) { rb_node_t *u = uncle(node); //LOG_DBG("inserting case 3\n"); if (u && u->color == RB_COLOR_RED) { rb_node_t *g; node->parent->color = RB_COLOR_BLACK; u->color = RB_COLOR_BLACK; g = grandparent(node); g->color = RB_COLOR_RED; rb_tree_insert_case1(g); } else { rb_tree_insert_case4(node); } }
static void insert_case3(struct RBTREE_TYPENAME* target, struct RBTREE_NODE* node) { struct RBTREE_NODE* U = uncle(node); struct RBTREE_NODE* G; DEBUG_RBTREE("insert_case3\n"); if (U != NULL && U->color == RED) { node->parent->color = BLACK; U->color = BLACK; G = grandparent(node); G->color = RED; insert_case1(target, G); } else { insert_case4(target, node); } }
/* * === FUNCTION ====================================================================== * Name: insert_case3 * Description: Covers the case that the parent and uncle are both RED * ===================================================================================== */ static void insert_case3 ( set * n ) { set * u = uncle(n); set * g; if((u != NULL ) && (u->color == RED)) { n->parent->color = BLACK; u->color = BLACK; g = grandparent(n); g->color = RED; insert_case1(g); } else { insert_case4(n); } } /* ----- end of static function insert_case3 ----- */
void insertRBNode(struct RBTree *tree, char *key, RBDATATYPE *data) { struct RBNode *n = insertRBNodeBinary(tree, key, data); if (!n) return; if (!n->parent) { //n->color = Black; return; } if (n->parent->color == Red) { struct RBNode *u = uncle(n); if (u && u->color == Red) { n->parent->color = Black; u->color = Black; if (n->parent->parent) n->parent->parent = Red; // Проверяем, не нарушает ли он (дед?) теперь балансировку. Если в результате этих перекрашиваний мы дойдём до корня, то в нём в любом случае ставим чёрный цвет. } else { // выполняем поворот. Если добавляемый узел был правым потомком, то необходимо сначала выполнить левое вращение, которое сделает его левым потомком } } }
/* 레드블랙트리 오류 수정 */ void treeFixUp(Tree *RBT, Node *node) { Node *p = node->parent; Node *u = uncle(node); Node *g = grandparent(node); // case1 : 삽입한 노드가 루트 노드인 경우 if (node == RBT->root) { node->color = BLACK; return; } // case2 : 삽입한 노드의 부모가 검은색인 경우 else if (p->color == BLACK) { return; } // case3 : 삽입한 노드와 부모 노드의 색이 빨간색인 경우 else if (node->color == RED && p->color == RED) { // case 3-1 : 삼촌 노드가 검은색인 경우 if (u->color == BLACK) { // case 3-1-1 : 현재 노드와 부모 노드의 방향이 반대인 경우 if (node == p->left && p == g->right) { rotateRight(RBT, node); node = p; } else if (node == p->right && p == g->left) { rotateLeft(RBT, node); node = p; } p = node->parent; u = uncle(node); g = grandparent(node); // case 3-1-2 : 현재 노드와 부모 노드의 방향이 직선인 경우 p->color = BLACK; g->color = RED; if (p == g->left) { rotateRight(RBT, p); } else if (p == g->right) { rotateLeft(RBT, p); } } // case 3-2 : 삼촌 노드가 빨간색인 경우 else { p->color = BLACK; u->color = BLACK; g->color = RED; treeFixUp(RBT, g); } } return; }
/* * An inserted node is always red. This violates maybe req. 2.) --> repairing necessary * Given a Node N to be inserted, it's Uncle (U), it's parent (P) and grandparent (GP), * five cases have to be considered: * 1.) root == NULL, (obvious) * 2.) The parent of N is black -> nothing to do * 3.) U and P of N is red -> color U,P black and GP red. -> req. 2.) maybe violated * then recursivley insert GP to the tree * 4.) N has non or a black U while N is the right child of his red P and P is left of GP * -> left rotation around P and apply case 5.) * 5.) N has non or a black U and is the left child of his red P and P is left of GP. * -> right rotation around GP. Then swap colors of former GP and P. */ void fix_rb_tree( Node *n ) { check(n, "Insert node: new_node == NULL"); Node *parent = n->parent; // case 1.) if(parent == NULL) { // debug("Insert node: case 1.)"); n->color = BLACK; return; } // case 2.) The parent is black. There is no need to fix the tree. if(parent->color == BLACK) { // debug("Insert node: case 2.)"); return; } // case 3.) U and P of N is red -> color U,P black and GP red. if(uncle(n)->color == RED) { // debug("Insert node: case 3.)"); n->parent->color = BLACK; uncle(n)->color = BLACK; grandparent(n)->color = RED; fix_rb_tree(grandparent(n)); return; } // case 4.) N has non or a black U while N is the right child of his red P and P is left of GP if( n == n->parent->right && n->parent == grandparent(n)->left ) { // debug("Fixing: case 4.) rotate left."); rotate_left(n->parent); n = n->left; } else if( n == n->parent->left && n->parent == grandparent(n)->right) { // debug("Fixing: case 4.) rotate right."); rotate_right(n->parent); n = n->right; } // 5.) N has non or a black U and is the left child of his red P and P is left of GP. n->parent->color = BLACK; grandparent(n)->color = RED; if( n == n->parent->left && n->parent == grandparent(n)->left ) { // debug("Fixing: case 5.) rotate right."); rotate_right(grandparent(n)); } else { // debug("Fixing: case 5.) rotate left."); rotate_left(grandparent(n)); } error: return; }
qrb_node * _rb_insert_item(QSP_ARG_DECL qrb_tree* tree_p, Item *ip ) { qrb_node * x_p; qrb_node * new_node_p; qrb_node * gp_p; // grandparent qrb_node * u_p; // uncle new_node_p = (qrb_node*) getbuf(sizeof(qrb_node)); // new_node_p->key = key; new_node_p->data = ip; new_node_p->left = NULL; new_node_p->right = NULL; MAKE_RED(new_node_p); binary_tree_insert(tree_p,new_node_p); x_p = new_node_p; while( 1 ){ if( IS_ROOT_NODE(x_p) ){ // wikipedia case 1 MAKE_BLACK(x_p); return new_node_p; } if( IS_BLACK(x_p->parent) ){ // wikipedia case 2 return new_node_p; } gp_p = grandparent(x_p); assert( gp_p != NULL ); u_p = uncle(x_p); // We know the parent is red if( IS_RED(u_p) ){ // wikipedia case 3 MAKE_BLACK(x_p->parent); MAKE_BLACK(u_p); MAKE_RED(gp_p); x_p = gp_p; // loop on grandparent } else { // uncle is black if( x_p == x_p->parent->left && x_p->parent == gp_p->left ){ // wikipedia case 5, left child of a left child rotate_right(tree_p,x_p->parent); MAKE_BLACK(x_p->parent); // new uncle is old grandparent MAKE_RED(gp_p); return new_node_p; } else if( x_p == x_p->parent->right && x_p->parent == gp_p->right ){ // wikipedia case 5 mirror image rotate_left(tree_p,x_p->parent); MAKE_BLACK(x_p->parent); // new uncle is old grandparent MAKE_RED(gp_p); return new_node_p; } else { // wikipedia case 4 if( x_p == x_p->parent->right ){ // right child of left child rotate_left(tree_p,x_p); x_p = x_p->left; } else { // left child of right child rotate_right(tree_p,x_p); x_p = x_p->right; } } } } // end tail recursion loop //MAKE_BLACK( RB_TREE_ROOT(tree) ); // NOTREACHED ??? /* tree_p->node_count ++; return new_node_p; */ } // rb_insert