学树状数组的话,可以看 英文的和 中文的(中文的很多啊,可以自己搜,只不过我觉得这篇比较好)
后来看到有些 blog(这个链接以前弄错了,在此表示不好意思)写到2352是入门题。
表示我一开始不会写,后来是看了人家的思路才写出来的-_-.
用树状数组,不用管y坐标(因为已经是升序,后边的星星不影响前边星星的等级),用level(n)来统计x坐标为n以前的星星个数,但是千万注意树状数组需要数组以1为首项,由于坐标有0,所以每次需要给x坐标+1(因为出现0会死循环)




还有一点就是那篇英文的介绍里面有点小错误,就是scale的第一个函数中,调用update时参数传反了
#include  < iostream >
using   namespace  std;
int  tree[ 32006 ];
int  level[ 32006 ];
int  n;
void  update( int  idx) // 更新,因为所有的都只会增加1,所以只用传一个参数就行了
{
       
while (idx  <=   32006 )
          {
              tree[idx]
++ ;
              idx 
+=  (idx  &  ( - idx));
          }
}
int  read( int  idx)
{
// 求一段数组的和
       int  sum  =   0 ;
      
while (idx  >   0 )
        {
            sum 
+=  tree[idx];
            idx 
-=  (idx  &  ( - idx));
        }
      
return  sum;
}
int  main( void )
{
      freopen(
" 2352.in " , " r " ,stdin);
      freopen(
" 2352.out " , " w " ,stdout);
      
int  x,y;
      scanf(
" %d " , & n);
      memset(tree,
0 , sizeof (tree));
      memset(level,
0 , sizeof (level));
      
for ( int  i  =   0 ;i  <  n;i ++ )
        {
            scanf(
" %d%d " , & x, & y);
            x
++ ; // 防止出现下标0
            level[read(x)] ++ ; // 先得到改点的level值
            update(x); // 更新以x为下标的tree数组值
        }
      
for ( int  i  =   0 ;i  <  n;i ++ )
        {
            printf(
" %d\n " ,level[i]); // 不用减1  因为我是先求在更新的
        }
    
return   0 ;
}