POJ 2481 Cows

转载请注明出处忆梦http://blog.csdn.net/yimeng2013/article/details/14517867


题目链接:http://poj.org/problem?id=2481

类型 : 单点修改,区间查询  

题目大意:对于N对区间(S,E),求满足对于i区间来说(Si,Ei),有多少对区间满足S<=Si && E>=Ei。如果S和E都相同,那么他们的这个值是一样的,也就是说E-S>Ei-Si

题解:现将E按降序排列,若E相等,按S的升序排列,那么对于当前的区间(Si,Ei),只需要求前面有多少个区间的S小于等于Si即可。注意考虑S和E都相等的区间。



#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define N 100005
int n;
int c[N];
int ans[N];
struct Node
{
	int x;
	int y;
	int id;
}node[N];

int lowbit(int x)
{
	return x & -x;
}

int sum(int x)
{
	int ret = 0;
	while(x > 0)
	{
		ret += c[x];
		x -= lowbit(x);
	}
	return ret;
}

void add(int x, int d)
{
	while(x <= N)
	{
		c[x] += d;
		x += lowbit(x);
	}
}


int cmp(Node a, Node b)
{
	if(a.y == b.y)
		return a.x < b.x;
	return a.y > b.y;
}
int main ()
{
	while(scanf("%d", &n),n)
	{
		memset(c, 0, sizeof(c));
		memset(ans, 0, sizeof(ans));
		for(int i = 1; i <= n; i++)
		{
			scanf("%d %d", &node[i].x, &node[i].y);
			node[i].id = i;
			node[i].x++;
			
		}
		
		sort(node+1, node+1+n, cmp);
		int temp ;
		for(int i = 1; i <= n; i++)
		{
			if(i>1 && node[i].x == node[i-1].x &&node[i].y==node[i-1].y)
			{
				ans[node[i].id] = temp;
				add(node[i].x,1);
			}
			else
			{
				temp = sum(node[i].x);
				ans[node[i].id] = temp;
				add(node[i].x,1);
			}
			
		}

		

		for(int i = 1; i < n; i++)
		{
			printf("%d ",ans[i] );
		}
		printf("%d\n", ans[n]);

	}
}


你可能感兴趣的:(POJ 2481 Cows)