Stars

Astronomers often examine star maps where stars are represented by points on a plane and each star has Cartesian coordinates. Let the level of a star be an amount of the stars that are not higher and not to the right of the given star. Astronomers want to know the distribution of the levels of the stars. 

 

For example, look at the map shown on the figure above. Level of the star number 5 is equal to 3 (it's formed by three stars with a numbers 1, 2 and 4). And the levels of the stars numbered by 2 and 4 are 1. At this map there are only one star of the level 0, two stars of the level 1, one star of the level 2, and one star of the level 3. 

You are to write a program that will count the amounts of the stars of each level on a given map.

Input

The first line of the input file contains a number of stars N (1<=N<=15000). The following N lines describe coordinates of stars (two integers X and Y per line separated by a space, 0<=X,Y <=32000). There can be only one star at one point of the plane. Stars are listed in ascending order of Y coordinate. Stars with equal Y coordinates are listed in ascending order of X coordinate.

Output

The output should contain N lines, one number per line. The first line contains amount of stars of the level 0, the second does amount of stars of the level 1 and so on, the last line contains amount of stars of the level N- 1.

Sample Input

5
1 1
5 1
7 1
3 3
5 5

Sample Output

1
2
1
1
0

这道题刚看的是时候认为可能用不了树状数组,后来看到一份梳妆数组资料中发现有这道原题,发现自己是在太弱了。题目中已经为你排号序,你所需要做的是计算每个点之前有几个点的横坐标不小于当前点。树状数组只能计算去区间和,而不能比较大小,肿么办?原来是用到了哈希的思想,。。。。用a[t]表明有多少个星星的x坐标为t。。(程序中可以省略此数组),然后用梳妆数组计算a[1]到a[t]之间的和即可。。。然而,很快把程序交上去之后,发现无线WA,搞不懂。。。。后来看了PKU的discuss中找到了答案,原来题目中给出0<=x<=32,000。。。。而树状数组显然不能处理0的情况,好吧,只能把横坐标+1。。。。。这道题对于初学者来讲,虽然很坑爹,但是非常经典。

#include 
#include 
#include 
#include 
#define N 32003
using namespace std;
int c[32007], num[32006];
void Update(int pos, int num)
{
    while(pos <= N)
    {
        c[pos] += num;
        pos += pos & (-pos);
    }
}

int Sum(int pos)
{
    int ans = 0;
    while(pos >= 1)
    {
        ans += c[pos];
        pos -= pos & (-pos);
    }
    return ans;
}

int main()
{
    int x, y;
    int n;

    while(scanf("%d", &n) != EOF)
    {
        memset(c, 0, sizeof(c));
        memset(num, 0, sizeof(num));
        for(int i = 1; i <= n; i++)
        {
            scanf("%d%d", &x, &y);
            x++;
            num[Sum(x)]++;
            Update(x, 1);
        }

        for(int j = 0; j < n;j++)
            printf("%d\n", num[j]);
    }


    return 0;
}

 

你可能感兴趣的:(树状数组)