POJ 2352 Stars 树状数组

题意:有很多给定坐标的星星,求每个星星左下方的星星数。
题解:用树形数组解。因为输入时y是升序,只要x1 >= x2 就可行。所以可以将二维视作一维,只考虑x就可以了。另外需要注意的是,树形数组不能从0开始,否则函数lowbit,和函数update死循环。这个问题可以将输入的x平移一个单位(即加1)来解决。

#include <memory> 
#include <cstdio>

int n, lev[16000],c[33000];

int lowbit ( int t )
{
	return t & ( t^(t-1) );  // t & ( -t );
}

void update ( int t )
{
	while ( t <= 32001 )
	{
		++c[t];
		t += lowbit(t);
	}
}

int getSum ( int t )
{
	int sum = 0;
	while ( t >= 1 )
	{
		sum += c[t];
		t -= lowbit(t);
	}
	return sum;  // 返回的sum加进了星星本身,所以最后从1开始输入,但结果依然正确。
}

int main()
{
	int i,x,y;
	scanf("%d",&n);
	memset(lev,0,sizeof(lev));
	memset(c,0,sizeof(c));
	for ( i = 1; i <= n; ++i )
	{
		scanf("%d%d",&x,&y);
		++x;  
		update(x);      //因为y是升序的,后面输入的星星一定不在此星星的左下方,所以后面的输入对现在求出的结果不产生影响
		lev[getSum(x)]++;
	}
	for ( i = 1; i <= n; ++i )   
		printf("%d\n",lev[i]);
	return 0;
}





评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值