Beispiel #1
0
        void SplayTree::remove(node* n)
        {
            // Fix up left-most and right-most node pointers if deleting
            // them.  We'll fix up the root in the node removal itself.
            if (unlikely(header.child[LEFT] == n))
            {
                header.child[LEFT] = successor(n);
            }
            if (unlikely(header.child[RIGHT] == n))
            {
                header.child[RIGHT] = predecessor(n);
            }

            // Decrement size count.
            (header_n()->data)--;

            // Find node to splice out of the tree.
            //    If n has one or no child, splice itself out, otherwise the
            //    successor.
            node* y = ((!n->child[LEFT]) || (!n->child[RIGHT])) ?
                            n : successor(n);

            // Find the subtree of y and link it with y's parent.
            node* x = y->child[LEFT] ? y->child[LEFT] : y->child[RIGHT];
            if (likely(NULL != x))
            {
                x->parent = y->parent;
            }
            if (unlikely(!y->parent))
            {
                // Fix root.
                header.parent = x;
            }
            else
            {
                y->parent->child[direction(y->parent, y)] = x;
            }

            // Replace n with y.
            if (likely(y != n))
            {
                y->parent = n->parent;
                if (y->parent)
                {
                    y->parent->child[direction(y->parent, n)] = y;
                }
                else
                {
                    // Removing root, so update header.
                    header.parent = y;
                }

                y->child[LEFT] = n->child[LEFT];
                if (y->child[LEFT])
                {
                    y->child[LEFT]->parent = y;
                }

                y->child[RIGHT] = n->child[RIGHT];
                if (y->child[RIGHT])
                {
                    y->child[RIGHT]->parent = y;
                }

                // Splay y up to the root.
                splay(y);
            }
        }
Beispiel #2
0
/** Get the root of the bst containing an item.
 *  @param i is an item in some bst
 *  @return the canonical element of the bst containing i; note that
 *  the operation restructures the tree possibly changing the root
 */
bst SaBstSet::find(index i) {
    assert(valid(i));
    return splay(i);
}
Beispiel #3
0
int main(){

	while(cin >> n){

		LCTInit();

		for (int i = 1;i <= n;i++) siz[i] = 1;

		for (int i = 1;i < n;i++){
			scanf("%d%d",&x,&y);
			link(x,y);
		}

		for (int i = 1;i <= n;i++)
			scanf("%d",&val[i]),mx[i] = sum[i] = val[i];

		int q; scanf("%d",&q);

		while(q--){
			int ty,z,x,y;
			scanf("%d",&ty);
			scanf("%d%d",&x,&y);
			if (ty == 1){
                if (root(x) == root(y)){
                    printf("-1\n");
                    continue;
                }
                link(x,y);
			}
			if (ty == 2){
                if (root(x) != root(y) || x == y){
                    printf("-1\n");
                    continue;
                }
				makeroot(x);
				cutf(y);
			}
			if (ty == 3){
				scanf("%d",&z);
                if (root(z) != root(y)){
                    printf("-1\n");
                    continue;
                }
				makeroot(y);
				access(z);
				splay(z);
				add(z,x);
			}
			if (ty == 4){
                if (root(x) != root(y)){
                    printf("-1\n");
                    continue;
                }
				makeroot(x);
				access(y);
				splay(y);
				printf("%d\n",mx[y]);
			}
		}
		printf("\n");
	}
}
inline root merge(root left, root right) {
    splay(left, left->siz);
    left->rson = right;
    left->maintain();
    return left;
}
Beispiel #5
0
/* If the hash is present nothing happens.
   Otherwise a new node is created for the hash picking one from the begin of the chain.
   Used nodes are moved to the end of the chain */
static inline void cacheset_add(struct cache_set *cs, unsigned char *md5, size_t size, uint32_t reclevel) {
    struct node *newnode;
    int64_t hash[2];

    memcpy(hash, md5, 16);
    if(splay(hash, size, cs)) {
	if(cs->root->minrec > reclevel)
	    cs->root->minrec = reclevel;
	return; /* Already there */
    }

    ptree("1:\n");
    if(printtree(cs, cs->root, 0)) {
	cli_errmsg("cacheset_add: inconsistent tree before choosing newnode, good luck\n");
	return;
    }

    newnode = cs->first;
    while(newnode) {
    	if(!newnode->right && !newnode->left)
    	    break;
    	newnode = newnode->next;
    }
    if(!newnode) {
	cli_errmsg("cacheset_add: tree has got no end nodes\n");
	return;
    }
    if(newnode->up) {
    	if(newnode->up->left == newnode)
    	    newnode->up->left = NULL;
    	else
    	    newnode->up->right = NULL;
    }
    if(newnode->prev)
    	newnode->prev->next = newnode->next;
    if(newnode->next)
    	newnode->next->prev = newnode->prev;
    if(cs->first == newnode)
    	cs->first = newnode->next;

    newnode->prev = cs->last;
    newnode->next = NULL;
    cs->last->next = newnode;
    cs->last = newnode;

    ptree("2:\n");
    if(printtree(cs, cs->root, 0)) {
	cli_errmsg("cacheset_add: inconsistent tree before adding newnode, good luck\n");
	return;
    }

    if(!cs->root) {
	newnode->left = NULL;
	newnode->right = NULL;
    } else {
	if(cmp(hash, size, cs->root->digest, cs->root->size) < 0) {
	    newnode->left = cs->root->left;
	    newnode->right = cs->root;
	    cs->root->left = NULL;
	} else {
	    newnode->right = cs->root->right;
	    newnode->left = cs->root;
	    cs->root->right = NULL;
	}
	if(newnode->left) newnode->left->up = newnode;
	if(newnode->right) newnode->right->up = newnode;
    }
    newnode->digest[0] = hash[0];
    newnode->digest[1] = hash[1];
    newnode->up = NULL;
    newnode->size = size;
    newnode->minrec = reclevel;
    cs->root = newnode;

    ptree("3: %lld\n", hash[1]);
    if(printtree(cs, cs->root, 0)) {
	cli_errmsg("cacheset_add: inconsistent tree after adding newnode, good luck\n");
	return;
    }
}
void cut_p(Splay *y) {
  access(y);
  splay(y);
  y->push();
  y->ch[0] = y->ch[0]->f = nil;
}
	Splay* splay() { nullinit(); splay(root); }
Beispiel #8
0
void expose(node*u,node*v){expose(u),splay(u),u->rev^=1;expose(v);splay(u);}
Beispiel #9
0
void merge(node*u,node*v){expose(v),splay(v),v->rev^=1,v->f=u;}
Beispiel #10
0
/* If the hash is not present nothing happens other than splaying the tree.
   Otherwise the identified node is removed from the tree and then placed back at 
   the front of the chain. */
static inline void cacheset_remove(struct cache_set *cs, unsigned char *md5, size_t size) {
    struct node *targetnode;
    struct node *reattachnode;
    int64_t hash[2];

    memcpy(hash, md5, 16);
    if(splay(hash, size, cs) != 1) {
	cli_dbgmsg("cacheset_remove: node not found in tree\n");
	return; /* No op */
    }

    ptree("cacheset_remove: node found and splayed to root\n");
    targetnode = cs->root;
    printnode("targetnode", cs, targetnode);

    /* First fix the tree */
    if(targetnode->left == NULL) {
        /* At left edge so prune */
        cs->root = targetnode->right;
        if(cs->root)
            cs->root->up = NULL;
    }
    else {
        /* new root will come from leftside tree */
        cs->root = targetnode->left;
        cs->root->up = NULL;
        /* splay tree, expecting not found, bringing rightmost member to root */
        splay(hash, size, cs);

        if (targetnode->right) {
            /* reattach right tree to clean right-side attach point */
            reattachnode = cs->root;
            while (reattachnode->right) 
                reattachnode = reattachnode->right; /* shouldn't happen, but safer in case of dupe */
            reattachnode->right = targetnode->right;
            targetnode->right->up = reattachnode;
        }
    }
    targetnode->size = (size_t)0;
    targetnode->digest[0] = 0;
    targetnode->digest[1] = 0;
    targetnode->up = NULL;
    targetnode->left = NULL;
    targetnode->right = NULL;

    /* Tree is fixed, so now fix chain around targetnode */
    if(targetnode->prev) 
        targetnode->prev->next = targetnode->next;
    if(targetnode->next) 
        targetnode->next->prev = targetnode->prev;
    if(cs->last == targetnode)
        cs->last = targetnode->prev;

    /* Put targetnode at front of chain, if not there already */
    if(cs->first != targetnode) {
        targetnode->next = cs->first;
        if(cs->first)
            cs->first->prev = targetnode;
        cs->first = targetnode;
    }
    targetnode->prev = NULL;

    printnode("root", cs, cs->root);
    printnode("first", cs, cs->first);
    printnode("last", cs, cs->last);

    printchain("remove (after)", cs);
}
Beispiel #11
0
void expose(node*u){for(node*v=NULL;u;u=u->f)splay(u),u->c[1]=v,(v=u)->upd();}
Beispiel #12
0
/** Return the last node in a path.
 *  @param q is the canonical element of some path
 *  @return the last node in the path containing q
 */
path PathSet::findtail(path q) {
	if (q == 0) return 0;
	while (right(q) != 0) q = right(q);
	return splay(q);
}
Beispiel #13
0
/** Return the canonical element of some path.
 *  @param i is a node in some path
 *  @return the node that is the canonical element of the path at the
 *  start of the operation; the operation performs a splay at i,
 *  so after the operation i is the canonical element.
 */
path PathSet::findpath(index i) { return splay(i); }
Beispiel #14
0
unsigned long long treeContains(node **root, unsigned long long value) {
  splay(root, value);
  return *root != 0 && (*root)->value == value;
}
Beispiel #15
0
void chroot(Splay *x){
  access(x);
  splay(x);
  x->rev ^= 1;
  x->push(); x->pull();
}
Beispiel #16
0
 bool contains(const K& k)
 {
   if (empty()) return false;
   splay(k, root);
   return root->key == k;
 }
Beispiel #17
0
void link(Splay *x, Splay *y){
  access(x);
  splay(x);
  chroot(y);
  x->setCh(y, 1);
}
Beispiel #18
0
void make_root(int u)
{
	access(u);
	splay(u);
	rev[u] ^= 1;
}
Beispiel #19
0
// The search function for Splay tree.  Note that this function
// returns the new root of Splay Tree.  If key is present in tree
// then, it is moved to root.
struct node *search(struct node *root, int key)
{
    return splay(root, key);
}
inline void R(int x,int y)
{
    Val(x)=y;
    splay(root,x);
}
	Splay* splayc(Splay* Root) { Splay* tmp=Root; return splay(tmp); }
Beispiel #22
0
// query[left, right]
inline int query_maxv(int left, int right) {
	splay(left - 1, right + 1);
	return head->ch[0]->ch[1]->maxv;
}
Beispiel #23
0
/*
 * Looks up the key i_inum in the splay tree, deletes the node
 * and reinserts it at the top. Also splays the previous entry in the
 * stack to the root.
 *
 * Input: Key to be looked up (i_inum) and current address.
 * Output: None
 * Side effects: Updates tree as described above.
 */
void
ref_tree(unsigned i_inum, md_addr_t addr)
{
  struct tree_node *ptr;
  int top, addr_above, pos, lstlft, at;

#ifdef PERF
  comp += 1.0;
#endif

  if (root->inum == i_inum)
    {
      ++out_stack[1];
      root->inum = t_entries;
    }
  else
    {
      top = addr_above = lstlft = 0;
      ptr = root;
      while (ptr)
	{
#ifdef PERF
	  comp += 1.0;
#endif
	  ++top;
	  p_stack[top] = ptr;
	  if (ptr->inum > i_inum)
	    {
	      addr_above += ptr->rtwt + 1;
	      lstlft = top;
	      ptr = ptr->lft;
	    }
	  else
	    {
	      if (ptr->inum == i_inum)
		{
		  addr_above += ptr->rtwt;
		  ++out_stack[addr_above + 1];
		  pos = top;
		  if (ptr->addr != addr)
		    fprintf(stderr,
			    "libcheetah: inconsistency w/ inum & addr'\n");
		  ptr->rtwt -= 1;
		  ptr = ptr->rt;
		  while (ptr)
		    {
		      ++top;
		      p_stack[top] = ptr;
		      ptr = ptr->lft;
		    }
		  break;
                }
	      ptr->rtwt -= 1;
	      ptr = ptr->rt;
	    }
        }

      if (pos == top)
	{
	  if (p_stack[top-1]->lft == p_stack[top])
	    p_stack[top-1]->lft = p_stack[top]->lft;
	  else
	    p_stack[top-1]->rt = p_stack[top]->lft;
	  at = lstlft;
        }
      else
	{
	  if (p_stack[top-1]->lft == p_stack[top])
	    p_stack[top-1]->lft = p_stack[top]->rt;
	  else
	    p_stack[top-1]->rt = p_stack[top]->rt;

	  p_stack[pos]->addr = p_stack[top]->addr;
	  p_stack[pos]->inum = p_stack[top]->inum;
	  at = top-1;
        }
      while (at > 1)
	{
#ifdef PERF
	  no_splay_steps += 1.0;   /* Counts the number of basic operations */
#endif
	  splay(at, p_stack);
	  at = at - 2;
        }
      root = p_stack[1];

      p_stack[top]->lft = root;
      p_stack[top]->rt = NULL;
      p_stack[top]->inum = t_entries;
      p_stack[top]->addr = addr;
      p_stack[top]->rtwt = 0;
      root = p_stack[top];
      /* traverse(root); */
    }
}
Beispiel #24
0
inline int _rank(node *root) {
	splay(root, null);
	return root->ch[0]->size + 1;
}
 void splay(Node *o){
   splay(o, root);
 }
Beispiel #26
0
inline void splay(int left, int right) {
	splay(find(right), null);
	splay(find(left), head);
}
Beispiel #27
0
void evert(Splay *x) {
  access(x);
  splay(x);
  x->rev ^= 1;
  x->push(); x->pull();
}
Beispiel #28
0
inline void makeRoot(Node* u)
{
	access(u);
	splay(u);
	u->revIt();
}
Beispiel #29
0
void access(int x){
	for (int y = 0;x;y = x,x = f[x])
		splay(x),son[x][1] = y,up(x);
}
Beispiel #30
0
		return Qnil;
		
	tree->root = splay(tree, tree->root, key);
	cmp = tree->compare_function(key, tree->root->key);
	if (cmp == 0) {
		return tree->root->value;
	}
	return Qnil;
}

static splaytree_node* delete(splaytree *tree, splaytree_node *n, VALUE key, VALUE *deleted) {
	int cmp, tsize;
	splaytree_node *x;
	
	tsize = n->size;
	n = splay(tree, n, key);
	cmp = tree->compare_function(key, n->key);
	if (cmp == 0) {
		*deleted = n->value;
		if (!n->left) {
			x = n->right;
		} else {
			x = splay(tree, n->left, key);
			x->right = n->right;
		}
		xfree(n);
		if (x) {
			x->size = tsize-1;
		}
		return x;
	}