2011-08-08 20:01:28
第一道树状数组,赤裸裸的树状数组
题目大意看了半天啊,曾一度想找个学英语的给我翻一下,原来看题都没有觉得这么难理解
这里贴一个有翻译的链接:http://www.docin.com/p-270244818.html
其实这道题图的样子和树状数组的图的样子是一样的,都是求左边的和下面的之和,画个图或许可以帮助理解
1 #include <iostream> 2 #include <stdio.h> 3 using namespace std; 4 int c[32005]; 5 int lowbit(int x) 6 { 7 return x &(-x); 8 } 9 10 int sum(int i)//前i项求和,从第一相开始求 11 { 12 int s=0; 13 while(i>0) 14 { 15 s=s+c[i]; 16 i=i-lowbit(i);//从右往左加,注意看图 17 } 18 return s; 19 } 20 21 void update(int i,int value) 22 { 23 while(i<=32005) 24 { 25 c[i]=c[i]+value; 26 i=i+lowbit(i);//从下往上更新,更新每一个点c[i],因为已经输入了一个点,所以在后面的点看来,左面或者下面已经有一个了 27 } 28 } 29 30 int level[32005]; 31 int main() 32 { 33 int Case; 34 //cin>>Case; 35 scanf("%d",&Case); 36 int x,y; 37 for(int i=0;i<Case;i++) 38 { 39 //cin>>x>>y; 40 scanf("%d%d",&x,&y); 41 int tmp=sum(++x);//这里是因为树状数组的下标是从1开始 42 level[tmp]++; 43 update(x,1); 44 } 45 for(int i=0;i<Case;i++) 46 { 47 //cout<<level[i]<<endl; 48 printf("%d\n",level[i]); 49 } 50 return 0; 51 }