poj Buy Tickets

样例输入:

4
0 77
1 51
1 33
2 69
4
0 20523
1 19243
1 3890
0 31492

样例输出:

77 33 69 51
31492 20523 3890 19243

题意:N个人,每个人可以排在第x位后(如果有人了,那就插队),这个人的编号为y。问最后队伍的顺序。

代码:

#include<stdio.h>
int p[200002],v[200002],ans[200002];
struct node {
	int l,r,n;
} a[800008];
void build(int k,int s,int e) {
	a[k].l=s;
	a[k].r=e;
	a[k].n=e-s+1;//n记录区间段的空位数 
	if(s==e) return;
	int m=(s+e)/2;
	build(k*2,s,m);
	build(k*2+1,m+1,e);
}
void insert(int k,int p,int v) {
	int l=a[k].l;
	int r=a[k].r;
	if(l==r) {//找到位置 
		a[k].n=0;// 
		ans[l]=v;// 
		return;
	}
	int m=(l+r)/2;
	if(a[2*k].n>=p) insert(k*2,p,v);//如果左枝空位足够,在左枝找 
	else insert(k*2+1,p-a[2*k].n,v);//否则去右枝找 
	a[k].n=a[k*2].n+a[k*2+1].n;//改变区间空位数 
}
int main() {
	int n;
	while(scanf("%d",&n)!=EOF) {
		build(1,1,n);
		for(int i=1; i<=n; i++) scanf("%d%d",&p[i],&v[i]);
		for(int i=n; i>0; i--)  insert(1,p[i]+1,v[i]);//倒序安排 
		for(int i=1; i<=n; i++) printf("%d%c",ans[i],i==n?'\n':' ');
	}
	return 0;
}

猜你喜欢

转载自blog.csdn.net/jack_jxnu/article/details/81297939