题意:维护两个栈,支持按插入时间合并
本来是左偏树的题,现在用treap水一下
把加入时间作为节点编号就可以很方便地实现了
#include<stdio.h>
#include<stdlib.h>
int l[100010],r[100010],fix[100010];
unsigned v[100010];
struct pair{
int l,r;
pair(int a=0,int b=0){l=a;r=b;}
};
pair split(int x,int d){
if(x==0)return pair();
pair s;
if(d<x){
s=split(l[x],d);
l[x]=s.r;
s.r=x;
}else{
s=split(r[x],d);
r[x]=s.l;
s.l=x;
}
return s;
}
void swap(int&a,int&b){a^=b^=a^=b;}
int merge(int x,int y){
if(x==0)return y;
if(y==0)return x;
if(fix[x]>fix[y])swap(x,y);
pair s=split(y,x);
l[x]=merge(l[x],s.l);
r[x]=merge(r[x],s.r);
return x;
}
int main(){
srand(19260817);
int cas,m,x,tot,rt[2];
pair p;
char s[10],st[4];
scanf("%d",&m);
cas=0;
while(m){
cas++;
printf("Case #%d:\n",cas);
tot=rt[0]=rt[1]=0;
while(m--){
scanf("%s",s);
if(s[1]==‘u‘){
tot++;
l[tot]=r[tot]=0;
fix[tot]=rand();
scanf("%s%u",st,v+tot);
rt[st[0]-‘A‘]=merge(rt[st[0]-‘A‘],tot);
}
if(s[1]==‘o‘){
scanf("%s",st);
for(x=rt[st[0]-‘A‘];r[x];x=r[x]);
p=split(rt[st[0]-‘A‘],x-1);
rt[st[0]-‘A‘]=p.l;
printf("%u\n",v[p.r]);
}
if(s[1]==‘e‘){
scanf("%s",st);
rt[st[0]-‘A‘]=merge(rt[0],rt[1]);
scanf("%s",st);
rt[st[0]-‘A‘]=0;
}
}
scanf("%d",&m);
}
}