Treap的动态平衡BST

//Treap的动态平衡树

#include<cstdio>
#include<cstdlib>

struct Node{
	Node *ch[2];					//左右子树
	int r;						//优先级。数值越大,优先级越高
	int v;						//值
/*	bool operator >(const Node& rhs)const {		//  根据优先级比较结点
		return r>rhs.r;
	}
*/	int cmp(int x)const{
		if(x==v)	return -1;
		return x<v?0:1;
	}
};

//d=0代表左旋,d=1代表右旋
void rotate(Node* &o,int d){
	Node *k=o->ch[d^1];	o->ch[d^1]=k->ch[d];	k->ch[d]=o;	o=k;
}

//在以o为根的子树中插入键值x,修改o
void insert(Node* &o,int x){
	if(o==NULL)
	{
		o=new Node();	o->ch[0]=o->ch[1]=NULL;	o->v=x;	o->r=rand();
	}
	else
	{
		int d=o->cmp(x);		//若可能有相同点,则不用cmp函数  int d=(x<o->v?0:1);
		insert(o->ch[d],x);
		if(o->ch[d]->r>o->r)
			rotate(o,d^1);
	}
};

void remove(Node* &o,int x){
	int d=o->cmp(x);
	if(d==-1){
		Node *u=o;
		if(o->ch[0]==NULL)	{	o=o->ch[1];		delete u; }
		else if(o->ch[1]==NULL)	{	o=o->ch[0];		delete u;}
		else{
			int d2=(o->ch[0]->r>o->ch[1]->r?1:0);
			rotate(o,d2);
			remove(o->ch[d2],x);
		}
	}
	else
		remove(o->ch[d],x);
}

//上面的代码没有处理"待插入值已经存在"和"待删除值不存在"这两种情况
//因此在调用相应函数之前如必要可进行一次查找
int find(Node *o,int x){
	while(o!=NULL){
		int d=o->cmp(x);
		if(d==-1)
			return 1;									//存在
		else o=o->ch[d];
	}
	return 0;											//不存在
}

void removetree(Node *&x)
{
	if(x->ch[0]!=NULL)	removetree(x->ch[0]);
	if(x->ch[1]!=NULL)	removetree(x->ch[1]);
	delete x;
	x=NULL;
}

int main()
{
	int n,i,x;
	Node *o=NULL;

	freopen("e:\\in.txt","r",stdin);
	while(scanf("%d",&n)==1)
	{
		for(i=1;i<=n;i++)
		{
			scanf("%d",&x);
			if(find(o,x)==0)
				insert(o,x);
			else
				printf("%d元素已存在!\n",x);
		}
		printf("插入完成\n");
		remove(o,12);
		for(i=1;i<=n;i++)
		{
			if(find(o,10+i)!=0)
			{
				printf("%d元素已存在!\n",10+i);
			}
		}
		removetree(o);
		for(i=1;i<=n;i++)
		{
			if(find(o,10+i)!=0)
			{
				printf("%d元素已存在!\n",10+i);
			}
		}
	}

	return 0;
}


你可能感兴趣的:(Treap的动态平衡BST)