警钟敲烂!!!
查看原帖
警钟敲烂!!!
655485
eifiwohie楼主2024/8/25 17:39
#include <bits/stdc++.h>
using namespace std;
int n;
struct node{
	int s[2];
	int p;
	int v;
	int cnt;
	int size;
	void init(int p1,int v1){
		p=p1;
		v=v1;
		cnt=size=1;
	}
}tr[1000005];
int root;
int idx;
void pushup(int x){
	tr[x].size=tr[tr[x].s[0]].size+tr[tr[x].s[1]].size+tr[x].cnt;
}
void rotate(int x){
	int y=tr[x].p,z=tr[y].p;
	int k=(tr[y].s[1]==x);
	tr[y].s[k]=tr[x].s[k^1];
	tr[tr[x].s[k^1]].p=y;
	tr[x].s[k^1]=y;
	tr[y].p=x;
	tr[z].s[tr[z].s[1]==y]=x;
	tr[x].p=z;
	pushup(y);
	pushup(x);
}
void splay(int x,int k){
	while(tr[x].p!=k){
		int y=tr[x].p;
		int z=tr[y].p;
		if(z!=k){
			(tr[y].s[0]==x)^(tr[z].s[0]==y)?rotate(x):rotate(y);
		}
		rotate(x);
	}
	if(k==0)root=x;
}
void find(int v){
	int x=root;
	while(tr[x].s[v>tr[x].v]&&v!=tr[x].v){
		x=tr[x].s[v>tr[x].v];
	}
	splay(x,0);
}
int get_pre(int v){
	find(v);
	int x=root;
	if(tr[x].v<v)return x;
	x=tr[x].s[0];
	while(tr[x].s[1])x=tr[x].s[1];
	splay(x,0);
	return x;
}
int get_suc(int v){
	find(v);
	int x=root;
	if(tr[x].v>v)return x;
	x=tr[x].s[1];
	while(tr[x].s[0])x=tr[x].s[0];
	splay(x,0);
	return x;
}
void del(int v){
	int pre=get_pre(v);
	int suc=get_suc(v);
	splay(pre,0);
	splay(suc,pre);
	int del=tr[suc].s[0];
	if(tr[del].cnt>1){
		tr[del].cnt--;
		splay(del,0);
	}else{
		tr[suc].s[0]=0;
		splay(suc,0);
	}
}

void insert(int v){
	int x=root;
	int p=0;
	while(x&&tr[x].v!=v){
		p=x,x=tr[x].s[v>tr[x].v];
	}
	if(x) tr[x].cnt++;
	else{
		x=++idx;
		tr[p].s[v>tr[p].v]=x;
		tr[x].init(p,v);
	}
	splay(x,0);
}
int get_rank(int v){
	insert(v);
	int res=tr[tr[root].s[0]].size;
	del(v);
	return res;
}
int get_val(int k){//第k小的 
	int x=root;
	while(1){
		int y=tr[x].s[0];
		if(tr[y].size+tr[x].cnt<k){
			k-=tr[y].size+tr[x].cnt;
			x=tr[x].s[1];
		}else{
			if(tr[y].size>=k)x=tr[x].s[0];
			else break;
		}
	}
	splay(x,0);
	return tr[x].v;
}
//int get_val2(int k){//第k大的 
//	int x=root;
//	while(1){
//		int y=tr[x].s[1];
//		if(tr[y].size+tr[x].cnt<k){
//			k-=tr[y].size+tr[x].cnt;
//			x=tr[x].s[0];
//		}else{
//			if(tr[y].size>=k)x=tr[x].s[1];
//			else break;
//		}
//	}
//	splay(x,0);
//	return tr[x]=v;
//}
int main() {
	insert(-1e9);insert(1e9);
	cin>>n;
	while(n--){
		int opt,x;
		cin>>opt>>x;
		if(opt==1)insert(x);
		if(opt==2)del(x);
		if(opt==3)cout<<get_rank(x)<<endl;
		if(opt==4)cout<<get_val(x+1)<<endl;
		if(opt==5)cout<<tr[get_pre(x)].v<<endl;
		if(opt==6)cout<<tr[get_suc(x)].v<<endl;
	}
	return 0;
}














调试了一整个下午,最后发现是第74行的splay(suc,pre);写成了splay(suc,0);直接T了6个点T_T

2024/8/25 17:39
加载中...