fhq treap求助...
查看原帖
fhq treap求助...
294562
EDqwq楼主2021/2/19 22:29
/*
  Author: EnderDeer
  Online Judge: Luogu
*/

#include<bits/stdc++.h>

using namespace std;

int read(){
   int s = 0,w = 1;
   char ch = getchar();
   while(ch < '0' || ch > '9'){if(ch == '-')w = -1;ch = getchar();}
   while(ch >= '0' && ch <= '9')s = s * 10 + ch - '0',ch = getchar();
   return s * w;
}

mt19937 rnd(time(0));

struct node{
	int l;
	int r;
	int w;
	int key;
	int siz;
}e[100010];

int cnt,rt;

int newnode(int w){
	cnt ++;
	e[cnt].w = w;
	e[cnt].key = rnd();
	e[cnt].siz = 1;
	return cnt; 
}

void update(int i){
	e[i].siz = e[e[i].l].siz + e[e[i].r].siz + 1;
}

void split(int i,int w,int &x,int &y){
	if(!i){
		x = y = 0;
		return ;
	}
	if(e[i].w <= w){
		x = i;
		split(e[i].r,w,e[i].r,y);
	}
	else {
		y = i;
		split(e[i].l,w,x,e[i].l);
	}
	update(i);
}

int merge(int x,int y){
	if(!x || !y)return x + y;
	if(e[x].key > e[y].key){
		e[x].r = merge(e[x].r,y);
		update(x);
		return x;
	}
	else {
		e[y].l = merge(x,e[y].l);
		update(y);
		return y;
	}
}

int x,y,z;

void ins(int w){
	split(rt,w,x,y);
	rt = merge(merge(x,newnode(w)),y);
}

void del(int w){
	split(rt,w,x,z);
	split(rt,w - 1,x,y);
	y = merge(e[y].l,e[y].r);
	rt = merge(merge(x,y),z);
}

int getrank(int w){
	split(rt,w - 1,x,y);
	int ans = e[x].siz + 1;
	rt = merge(x,y);
	return ans;
}

int getnum(int rk){
	int now = rt;
	while(now){
		if(e[e[now].l].siz + 1 == rk)break;
		else if(e[e[now].l].siz >= rk)now = e[now].l;
		else {
			rk -= e[e[now].l].siz + 1;
			now = e[now].r;
		}
	}
	return e[now].w;
}

int pre(int w){
	split(rt,w - 1,x,y);
	int now = x;
	while(e[now].r)now = e[now].r;
	int ans = e[now].w;
	rt = merge(x,y);
	return ans;
}

int nxt(int w){
	split(rt,w,x,y);
	int now = y;
	while(e[now].l)now = e[now].l;
	int ans = e[now].w;
	rt = merge(x,y);
	return ans;
}

int n;

signed main(){
	cin>>n;
	for(int i = 1;i <= n;i ++){
		int op,w;
		op = read(),w = read();
		if(op == 1){
			ins(w);
		}
		if(op == 2){
			del(w);
		}
		if(op == 3){
			printf("%lld\n",getrank(w));
		}
		if(op == 4){
			printf("%lld\n",getnum(w));
		}
		if(op == 5){
			printf("%lld\n",pre(w));
		}
		if(op == 6){
			printf("%lld\n",nxt(w));
		}
	}
	return 0;
}
2021/2/19 22:29
加载中...