默写splay板子
很多细节问题。。。
#include<cstdio> #include<iostream> using namespace std; #define maxn 1000005 int root; int tot=0; int ch[maxn][2],par[maxn]; int cnt[maxn],size[maxn]; int val[maxn],dat[maxn]; void pushup(int x) { size[x]=cnt[x]+size[ch[x][0]]+size[ch[x][1]]; }///size信息 bool which(int x) { return ch[par[x]][1]==x; } void rotate(int x) { int y=par[x],z=par[y];///? int w=which(x); int t=ch[x][w^1]; par[t]=y; ch[y][w]=t; //par[t]=y; par[x]=z; ch[z][which(y)]=x; //par[x]=z; par[y]=x; ch[x][w^1]=y; //par[y]=x; pushup(y); pushup(x); } void splay(int x,int goal=0) { if(x==0)return; int y,z; while(par[x]!=goal)///为什么不是x { // cout<<"PAR"<<par[x]<<endl; y=par[x],z=par[y]; //cout<<x<<y<<z<<"YZ"<<endl; if(z!=goal) ///??? { if(which(x)==which(y)) { rotate(y); } else rotate(x); } rotate(x); // x=par[x]; // y=par[y]; } if(!goal)root=x; } void find(int x) { int cur=root; while(ch[cur][x>val[cur]]&&x!=val[cur]) { cur=ch[cur][x>val[cur]]; }///为什么不维护父节点了? splay(cur); } int pre(int x) { find(x); int cur=ch[root][0]; if(!cur)return 0;///直接返回0 //cout<<root<<" pre "<<ch[root][0]<<endl; while(ch[cur][1]) { cur=ch[cur][1]; } return cur; } int succ(int x) { find(x); int cur=ch[root][1]; if(!cur)return 0; //cout<<root<<" pre "<<ch[root][1]<<endl; while(ch[cur][0]) { cur=ch[cur][0]; } return cur; } void dfs(int cur) { //cout<<cur<<"cur"<<" ch "<<ch[cur][1]<<endl; if(ch[cur][0])dfs(ch[cur][0]); cout<<val[cur]<<" "<<dat[cur]<<' '; if(ch[cur][1])dfs(ch[cur][1]); } void del(int x) { //cout<<root<<"END"<<endl; int p=pre(x),s=succ(x);///后缀为0???前驱为0??? // cout<<p<<" PS "<<s<<endl; if(!s) { if(!p) { ch[root][0]=ch[root][1]=root=0;///只有一个点 return; } splay(p);///没有后缀 ch[root][1]=0; return; }///??? //cout<<x<<endl; //cout<<p<<s<<endl; splay(p); splay(s,p); int de=ch[s][0]; if(cnt[de]>1) { cnt[de]--; splay(de); } else ch[s][0]=0; //par[ch[root][1]]=root; //pushup(root); } void ins(int x,int d) { int cur=root,p=0;///维护父节点信息 while(cur&&(x!=val[cur])) { p=cur; cur=ch[cur][x>val[cur]];///>号 } if(cur) { cnt[cur]++; } else { cur=++tot; //cout<<p<<"父亲"<<endl; if(p)ch[p][x>val[p]]=cur;///判一下p是否为0 ch[cur][0]=ch[cur][1]=0; par[cur]=p;///注意维护下父节点 val[cur]=x; dat[cur]=d; size[cur]=1; cnt[cur]=1; // dfs(root); splay(cur); } // cout<<"DFS"<<endl; //dfs(root); } int mi() { int cur=root; if(!cur)return 0; while(ch[cur][0]) { cur=ch[cur][0]; } int ans=dat[cur]; del(val[cur]); return ans; } int ma() { int cur=root; if(!cur)return 0; while(ch[cur][1]) { cur=ch[cur][1]; } int ans=dat[cur]; //cout<<ans<<endl; del(val[cur]); //dfs(root); return ans; } int main() { int n,d,p; while(scanf("%d",&n)!=EOF) { if(n==0)break; else if(n==1) { scanf("%d%d",&d,&p); ins(p,d); } else if(n==2) { cout<<ma()<<' '; } else if(n==3) { cout<<mi()<<' '; } } }