从结束状态推向起始状态
可以发现,这个过程中,
只要给之前的状态留下足够的空位,
就可以实现无冲突的放置方案
#include<cstdio>
#include<cstdlib>
#include<cstring>
using namespace std;
const int MAXN = 200005;
int val[MAXN] , pos[MAXN] ;
int tree[MAXN<<2];
int seq[MAXN];
inline void insert(const int &value,const int pos,const int ll,const int rr,const int si)
{
if(ll == rr)
{
tree[si] = 0;
seq[ll] = value;
}
else
{
int mid = (ll + rr)>>1;
int p = tree[si<<1];
if(p <= pos)
insert(value, pos - p , mid+1, rr ,(si<<1)|1);
else//p > pos
insert(value, pos ,ll , mid ,(si<<1));
tree[si]--;
}
}
inline void build(const int ll,const int rr,const int si)
{
if(ll == rr)
{
tree[si] = 1;
}
else
{
tree[si] = rr - ll + 1;
int mid = (ll + rr)>>1;
if(ll <= mid)build(ll, mid, si<<1);
if(mid < rr)build(mid+1,rr,(si<<1)|1);
}
}
int main()
{
int n;
#ifndef ONLINE_JUDGE
freopen("poj2828.in","r",stdin);
freopen("poj2828.out","w",stdout);
#endif
while(scanf("%d",&n)!=EOF)
{
// memset(val,0,sizeof(val));
// memset(pos,0,sizeof(pos));
// memset(seq,0,sizeof(seq));
// memset(tree,0,sizeof(tree));
build(1, n, 1);
for(int i = 1;i <= n;i++)
scanf("%d%d",&pos[i],&val[i]);
for(int i = n;i >= 1;i--)
{
insert(val[i], pos[i], 1, n, 1);
}
for(int i = 1;i < n;i++)
{
printf("%d ",seq[i]);
}
printf("%d\n",seq[n]);
}
#ifndef ONLINE_JUDGE
fclose(stdin);
fclose(stdout);
#endif
return 0;
}