最后的人的位置一定是固定的,所以倒序插入,插入之后这个位置就不参与计数了,所以问题变成,找到第 i 个空位,线段树记录该区间里有几个空位。
#include <stdio.h>
#define maxn 200010
int sum[4*maxn];
int pos[maxn],val[maxn];
int ans[maxn];
void pushup(int o)
{
sum[o]=sum[o*2]+sum[o*2+1];
}
void build(int l,int r,int o)
{
if(l==r)
{
sum[o]=1;
return;
}
else
{
int m=(l+r)/2;
build(l,m,o*2);
build(m+1,r,o*2+1);
pushup(o);
}
}
int query(int p,int l,int r,int o)
{
if(l==r)
{
sum[o]=0;
return l;
}
else
{
int m=(l+r)/2,rank;
if(sum[o*2]>p) rank=query(p,l,m,o*2);
else rank=query(p-sum[o*2],m+1,r,o*2+1);
pushup(o);
return rank;
}
}
int main()
{
int n;
int i;
while(scanf("%d",&n)!=EOF)
{
for(i=1;i<=n;i++)
scanf("%d%d",&pos[i],&val[i]);
build(0,n-1,1);
for(i=n;i>0;i--)
{
int x=query(pos[i],0,n-1,1);
ans[x]=val[i];
//printf("%d %d\n",x,val[i]);
}
printf("%d",ans[0]);
for(i=1;i<n;i++) printf(" %d",ans[i]);
printf("\n");
}
return 0;
}