题意:维护两个栈,支持按插入时间合并
本来是左偏树的题,现在用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); } }