UAPC 2011 J The Incubator
問題
次のようなクエリに答えよ。
- 先頭の値を削除
- 末尾に値xを挿入する
- x番目の値を消去する
- xの値をもつ要素を消去する
- x番目の値を答える
制約条件
クエリの数≦40万
方針
普通の配列 + binary indexed tree + map
まだ生きている要素をbinary indexed treeでフラグを立てて管理しておいて、
x番目の要素を削除(or表示)するときは、二分探索。
xの値を持つ要素の削除は、mapでxの値とインデックスを関連づけておいて行う。
ソースコード
int q,lim; int bit[400001],num[400000],sz,tl; void add(int i,int x){ for(;i<=q;i+=i&-i)bit[i]+=x; } int sum(int i){ int ret=0; for(;i;i-=i&-i)ret+=bit[i]; return ret; } int get(int x){ int lo=0, hi=tl, mid; while(lo+1<hi){ mid=(lo+hi)/2; if(sum(mid)<x)lo=mid; else hi=mid; } return lo; } int main() { while(scanf("%d%d",&q,&lim),q){ memset(bit,0,sizeof(bit)); map<int,int> pos; sz=tl=0; rep(it,q){ int query,x; scanf("%d%d",&query,&x); if(query==0){ pos[x]=tl; num[tl++]=x; add(tl,1); if(sz>=lim){ add(get(1)+1,-1); } else sz++; } if(query==1){ add(get(x)+1,-1); sz--; } if(query==2){ printf("%d\n",num[get(x)]); } if(query==3){ add(pos[x]+1,-1); sz--; } } puts("end"); } return 0; }