【树状数组】数星星(POJ2352 star)
比如上图,5号星星的等级为3(其左下角有编号为1、2、4的星星共三颗)。2号星星和4号星星的等级为1。在上图中只有一颗星星等级为0,两颗星星等级为1,一颗星星等级为2,一颗星星等级为3。
给定一个星象图,请你写一个程序计算各个等级的星星数目。
Input
输入的第一行包含星星的总数N (1<=N<=15000)。接下来N行,描述星星的坐标(X,Y)(X和Y用空格分开,0<=X,Y<=32000)。星象图中的每个点处最多只有一颗星星。所有星星按Y坐标升序排列。Y坐标相等的星星按X坐标升序排列。
Output
输出包含N行,每行一个整数。第一行包含等级0的星星数目,第二行包含等级1的星星数目,依此类推,最后一行包含等级为N-1的星星数目。
树状数组。因为Y坐标已经有序,所以直接统计当前star输入后,其x坐标左侧的星星数量(前面输入的star一定比后面的y坐标小。)然后+1即可,注意x坐标要左移1。因为数据存在x=0的情况。
天文学家经常观察星象图。星象图中用平面上的点来表示一颗星星,每一颗星星都有一个笛卡尔坐标。设定星星的等级为其左下角星星的总数。
天文学家们想知道星星等级的分布情况。
![](https://i-blog.csdnimg.cn/blog_migrate/fd47938575a43734c7155490c64a749e.jpeg)
比如上图,5号星星的等级为3(其左下角有编号为1、2、4的星星共三颗)。2号星星和4号星星的等级为1。在上图中只有一颗星星等级为0,两颗星星等级为1,一颗星星等级为2,一颗星星等级为3。
给定一个星象图,请你写一个程序计算各个等级的星星数目。
Input
输入的第一行包含星星的总数N (1<=N<=15000)。接下来N行,描述星星的坐标(X,Y)(X和Y用空格分开,0<=X,Y<=32000)。星象图中的每个点处最多只有一颗星星。所有星星按Y坐标升序排列。Y坐标相等的星星按X坐标升序排列。
Output
输出包含N行,每行一个整数。第一行包含等级0的星星数目,第二行包含等级1的星星数目,依此类推,最后一行包含等级为N-1的星星数目。
Sample Input
5 1 1 5 1 7 1 3 3 5 5
Sample Output
1 2 1 1 0
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
int c[40000],N;
int level[40000];
int lowbit(int x)
{
return x & -x;
}
int getsum(int num)
{
int sum = 0;
while(num > 0)
{
sum += c[num];
num -= lowbit(num);
}
return sum;
}
void update(int num,int val)
{
while(num <= 36000)
{
c[num] += val;
num += lowbit(num);
}
}
int main()
{
while(scanf("%d",&N) != EOF)
{
memset(c,0,sizeof(c));
memset(level,0,sizeof(level));
for(int i = 1; i <= N; i++)
{
int x,y;
scanf("%d%d",&x,&y);
x++;//防止x=0,lowbit(0)会死循环
level[getsum(x)]++;
update(x,1);
}
for(int i = 0; i < N; i++ )
{
printf("%d\n",level[i]);
}
}
return 0;
}