《信息学奥赛一本通·提高篇》——数据结构——树状数组——例题2数星星Stars(urall1028)——第213面

思路:
x,y坐标按升序排列,故可把二维树状转化为一维树状。

#include<iostream> using namespace std; const int maxn=32005; int n,a[maxn]; int ans[maxn],c[maxn]; struct node { int x;int y; }p[maxn]; int lowbit(int x) { return x&(-x); } void change(int index,int v) { for(int i=index;i<=maxn;i+=lowbit(i)) //错在此处—把maxn错设为n,因为x的范围不能确定,故直接加到范围最大值 c[i]+=v; } int sum(int index) { int s=0; for(int i=index;i>0;i-=lowbit(i)) s+=c[i]; return s; }
//main函数理解至关重要!!! int main() { cin>>n; int x,y; for(int i=1;i<=n;i++) cin>>p[i].x>>p[i].y; for(int i=1;i<=n;i++) { int u=p[i].x+1; //官方话:树状无法维护下标为0的元素 //简单理解:把x坐标统一向右移一个单位就odk了 int v=sum(u); //此时还没有录进当前点!!!!!! //y是按升序排列 //算出左下点个数(这就可以包括正左和正下点啦)(并且不包括当前点(因为他还没被录进去咻咻咻)) ans[v]++; //记录等级相同点的个数 change(u,1); //把当前点录进去 //一定要等算好等级后再录进去点!!!! } for(int i=0;i<n;i++) cout<<ans[i]<<endl; return 0; }
原文地址:https://www.cnblogs.com/konglingyi/p/11262607.html