1. 程式人生 > >Buy Tickets POJ - 2828線段樹求插隊

Buy Tickets POJ - 2828線段樹求插隊

題意就是給你n個人,每個人有自己的要插入的pos和val,問你最後的排序

思路:逆序插入,最後一個人的位置一定是固定的,因為必須連續插入,所以第i個人插入的時候必須保證前面有pos[i]個空位,

那麼用線段樹記錄位置個數,如果位置不夠,就往後挪。

#include<iostream>
#include<cstdio>
using namespace std;

#define N 200005

int spare[N<<2];
int seq[N];
int pos[N],val[N];

void pushdown(int rt)
{
        spare[rt]
=spare[rt*2]+spare[rt*2+1]; } void build(int rt,int l,int r) { if(l==r) { spare[rt]=1; return; } int mid=(l+r)/2; build(rt*2,l,mid); build(rt*2+1,mid+1,r); pushdown(rt); } void insert(int pos,int val,int
rt,int l,int r) { if(l==r) { seq[l]=val; spare[rt]=0; return; } int mid=(l+r)/2; if(pos<spare[rt*2]) { insert(pos,val,rt*2,l,mid); } else { insert(pos
-spare[rt*2],val,rt*2+1,mid+1,r); } pushdown(rt); } int main() { int n; while(~scanf("%d",&n)) { build(1,1,n); for (int i=0; i<n ; i++ ) { scanf("%d %d",&pos[i],&val[i]); } for (int i=n-1;i>=0 ;i-- ) { insert(pos[i],val[i],1,1,n); } for (int i=1;i<=n ;i++ ) { if(i==n) { printf("%d\n",seq[i]); } else printf("%d ",seq[i]); } } return 0; }