Ejemplo n.º 1
0
/*
 * Operations INSERT and DELETE, when run on a tree with n keys,
 * take O(logN) time.Because they modify the tree, the result
 * may violate the red-black properties.To restore these properties,
 * we must change the colors of some of the nodes in the tree
 * and also change the pointer structure.
 */
static void interval_insert_color(struct interval_node *node,
				  struct interval_node **root)
{
	struct interval_node *parent, *gparent;

	while ((parent = node->in_parent) && node_is_red(parent)) {
		gparent = parent->in_parent;
		/* Parent is RED, so gparent must not be NULL */
		if (node_is_left_child(parent)) {
			struct interval_node *uncle;

			uncle = gparent->in_right;
			if (uncle && node_is_red(uncle)) {
				uncle->in_color = INTERVAL_BLACK;
				parent->in_color = INTERVAL_BLACK;
				gparent->in_color = INTERVAL_RED;
				node = gparent;
				continue;
			}

			if (parent->in_right == node) {
				__rotate_left(parent, root);
				interval_swap(node, parent);
			}

			parent->in_color = INTERVAL_BLACK;
			gparent->in_color = INTERVAL_RED;
			__rotate_right(gparent, root);
		} else {
			struct interval_node *uncle;

			uncle = gparent->in_left;
			if (uncle && node_is_red(uncle)) {
				uncle->in_color = INTERVAL_BLACK;
				parent->in_color = INTERVAL_BLACK;
				gparent->in_color = INTERVAL_RED;
				node = gparent;
				continue;
			}

			if (node_is_left_child(node)) {
				__rotate_right(parent, root);
				interval_swap(node, parent);
			}

			parent->in_color = INTERVAL_BLACK;
			gparent->in_color = INTERVAL_RED;
			__rotate_left(gparent, root);
		}
	}

	(*root)->in_color = INTERVAL_BLACK;
}
Ejemplo n.º 2
0
static void __remove(treap_head **pp)
{
   assert(pp);
   while (1) {
      if (!pp || !*pp)
         return;
      else if (!(*pp)->left && !(*pp)->right) {
         *pp = (*pp)->parent = NULL;
      } else if (!(*pp)->left) {
         __rotate_left(pp);
         pp = &(*pp)->left;
      } else if (!(*pp)->right) {
         __rotate_right(pp);
         pp = &(*pp)->right;
      } else if ((*pp)->left->priority > (*pp)->right->priority) {
         __rotate_right(pp);
         pp = &(*pp)->right;
      } else {
         __rotate_left(pp);
         pp = &(*pp)->left;
      }
   }
}
Ejemplo n.º 3
0
treap_head * treap_insert(treap_tree *tree, treap_head *node)
{
   unsigned long key;
   treap_head **pp, *parent;
   assert(tree && node);

   if (!tree || !node)
      return null_head;

   treap_init(node);

   key = __TREAP_KEY(tree, node);
   parent = tree->root;
   pp = &tree->root;
   while (*pp) {
      int __cmp = __TREAP_CMP(tree, key, __TREAP_KEY(tree, *pp));
      if (__cmp == 0 && tree->unique)
         return null_head;
      if (__cmp <= 0) {
         parent = *pp;
         pp = &(*pp)->left;
      } else {
         parent = *pp;
         pp = &(*pp)->right;
      }
   }
   *pp = node;
   node->parent = parent;

   while (1) {
      if (!*pp)
         return node;
      else if ((*pp)->left && (*pp)->left->priority > (*pp)->priority)
         __rotate_right(pp);
      else if ((*pp)->right && (*pp)->right->priority > (*pp)->priority)
         __rotate_left(pp);

      if (!(*pp)->parent)
         return node;
      else if (!(*pp)->parent->parent)
         pp = &tree->root;
      else if ((*pp)->parent == (*pp)->parent->parent->left)
         pp = &(*pp)->parent->parent->left;
      else if ((*pp)->parent == (*pp)->parent->parent->right)
         pp = &(*pp)->parent->parent->right;
   }
   return node;
}
Ejemplo n.º 4
0
static void interval_erase_color(struct interval_node *node,
				 struct interval_node *parent,
				 struct interval_node **root)
{
	struct interval_node *tmp;

	while (node_is_black_or_0(node) && node != *root) {
		if (parent->in_left == node) {
			tmp = parent->in_right;
			if (node_is_red(tmp)) {
				tmp->in_color = INTERVAL_BLACK;
				parent->in_color = INTERVAL_RED;
				__rotate_left(parent, root);
				tmp = parent->in_right;
			}
			if (node_is_black_or_0(tmp->in_left) &&
			    node_is_black_or_0(tmp->in_right)) {
				tmp->in_color = INTERVAL_RED;
				node = parent;
				parent = node->in_parent;
			} else {
				if (node_is_black_or_0(tmp->in_right)) {
					struct interval_node *o_left;

					o_left = tmp->in_left;
					if (o_left)
						o_left->in_color = INTERVAL_BLACK;
					tmp->in_color = INTERVAL_RED;
					__rotate_right(tmp, root);
					tmp = parent->in_right;
				}
				tmp->in_color = parent->in_color;
				parent->in_color = INTERVAL_BLACK;
				if (tmp->in_right)
					tmp->in_right->in_color = INTERVAL_BLACK;
				__rotate_left(parent, root);
				node = *root;
				break;
			}
		} else {
			tmp = parent->in_left;
			if (node_is_red(tmp)) {
				tmp->in_color = INTERVAL_BLACK;
				parent->in_color = INTERVAL_RED;
				__rotate_right(parent, root);
				tmp = parent->in_left;
			}
			if (node_is_black_or_0(tmp->in_left) &&
			    node_is_black_or_0(tmp->in_right)) {
				tmp->in_color = INTERVAL_RED;
				node = parent;
				parent = node->in_parent;
			} else {
				if (node_is_black_or_0(tmp->in_left)) {
					struct interval_node *o_right;

					o_right = tmp->in_right;
					if (o_right)
						o_right->in_color = INTERVAL_BLACK;
					tmp->in_color = INTERVAL_RED;
					__rotate_left(tmp, root);
					tmp = parent->in_left;
				}
				tmp->in_color = parent->in_color;
				parent->in_color = INTERVAL_BLACK;
				if (tmp->in_left)
					tmp->in_left->in_color = INTERVAL_BLACK;
				__rotate_right(parent, root);
				node = *root;
				break;
			}
		}
	}
	if (node)
		node->in_color = INTERVAL_BLACK;
}
Ejemplo n.º 5
0
static
void
__rb_del_fix(rbtree_t *T, rbtree_node_t *x)
{
    rbtree_node_t *w;

    while ((x != T->root) && (COLOR(x) == BLACK))
        {
            if (x == x->p->l)
                {
                    w = x->p->r;
                    if (COLOR(w) == RED)
                        {
                            MAKE_BLACK(w);
                            MAKE_RED  (x->p);
                            __rotate_left(T, x->p);
                            w = x->p->r;
                        }
                    if ((COLOR(w->l) == BLACK) && (COLOR(w->r) == BLACK))
                        {
                            MAKE_RED(w);
                            x = x->p;
                        }
                    else
                        {
                            if (COLOR(w->r) == BLACK)
                                {
                                    MAKE_BLACK(w->l);
                                    MAKE_RED  (w);
                                    __rotate_right(T, w);
                                    w = x->p->r;
                                }

                            w->color = COLOR(x->p);

                            MAKE_BLACK(x->p);
                            MAKE_BLACK(w->r);
                            __rotate_left(T, x->p);
                            x = T->root;
                            break;
                        }
                }
            else
                {
                    w = x->p->l;
                    if (COLOR(w) == RED)
                        {
                            MAKE_BLACK(w);
                            MAKE_RED  (x->p);
                            __rotate_right(T, x->p);
                            w = x->p->l;
                        }
                    if ((COLOR(w->l) == BLACK) && (COLOR(w->r) == BLACK))
                        {
                            MAKE_RED(w);
                            x = x->p;
                        }
                    else
                        {
                            if (COLOR(w->l) == BLACK)
                                {
                                    MAKE_BLACK(w->r);
                                    MAKE_RED  (w);
                                    __rotate_left(T, w);
                                    w = x->p->l;
                                }
                            w->color = COLOR(x->p);
                            MAKE_BLACK(x->p);
                            MAKE_BLACK(w->l);
                            __rotate_right(T, x->p);
                            x = T->root;
                            break;
                        }
                }
        }

    MAKE_BLACK(x);
}
Ejemplo n.º 6
0
static
void
__rb_insert (rbtree_t *T, PyObject *k, PyObject *v)
{
    rbtree_node_t *x, *y;

    Py_INCREF(k);
    Py_INCREF(v);

    x = __tree_insert(T, k, v);
    if (x ==  NULL) {
        return;
    }


    MAKE_RED  (x);

    while ((x != T->root) && (COLOR(x->p) == RED))
	{
	    if (x->p == x->p->p->l)
		{
		    y = x->p->p->r;
		    if (COLOR(y) == RED)
			{
			    MAKE_BLACK(x->p);
			    MAKE_BLACK(y);
			    MAKE_RED  (x->p->p);
			    x = x->p->p;
			}
		    else
			{
			    if (x == x->p->r)
				{
				    x = x->p;
				    __rotate_left(T, x);
				}
			    MAKE_BLACK(x->p);
			    MAKE_RED  (x->p->p);
			    __rotate_right(T, x->p->p);
			    break;
			}
		}
	    else
		{
		    y = x->p->p->l;
		    if (COLOR(y) == RED)
			{
			    MAKE_BLACK(x->p);
			    MAKE_BLACK(y);
			    MAKE_RED  (x->p->p);
			    x = x->p->p;
			}
		    else
			{
			    if (x == x->p->l)
				{
				    x = x->p;
				    __rotate_right(T, x);
				}
			    MAKE_BLACK(x->p);
			    MAKE_RED  (x->p->p);
			    __rotate_left(T, x->p->p);
			    break;
			}
		}
	}

    MAKE_BLACK(T->root);
}