题意:二维的树状数组
注意的有三个地方,
输入进去的坐标都加1,防止lowbit(0) + 0造成死循环
还有就是询问矩形面积的时候,输入进去的x1,x2,y1,y2,可能不是正对角线,要转化成正对角线
初始化的时候,是每个点的值为1
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include <cmath> 5 #include<stack> 6 #include<vector> 7 #include<map> 8 #include<set> 9 #include<queue> 10 #include<algorithm> 11 using namespace std; 12 13 typedef long long LL; 14 const int INF = (1<<30)-1; 15 const int mod=1000000007; 16 const int maxn=10005; 17 18 int a[1005][1005],c[1005][1005]; 19 20 int lowbit(int x){ return x & (-x);} 21 22 int sum(int x,int y){ 23 int ret=0; 24 for(int i=x;i>0;i-=lowbit(i)) 25 for(int j=y;j>0;j-=lowbit(j)) 26 ret+=c[i][j]; 27 28 return ret; 29 } 30 31 void add(int x,int y,int d){ 32 for(int i=x;i<1005;i+=lowbit(i)) 33 for(int j=y;j<1005;j+=lowbit(j)) 34 c[i][j]+=d; 35 } 36 37 void init(){ 38 memset(c,0,sizeof(c)); 39 for(int i=1;i<1005;i++){ 40 for(int j=1;j<1005;j++){ 41 add(i,j,1); 42 a[i][j] = 1; 43 } 44 } 45 } 46 47 int main(){ 48 int T; 49 int kase = 0; 50 scanf("%d",&T); 51 while(T--){ 52 printf("Case %d:\n",++kase); 53 init(); 54 int m; 55 scanf("%d%*c",&m); 56 while(m--){ 57 char cmd; 58 scanf("%c",&cmd); 59 if(cmd == 'S') { 60 int x,xx,y,yy,x1,x2,y1,y2; 61 scanf("%d%d%d%d%*c",&x,&y,&xx,&yy); 62 x++;y++;xx++;yy++; 63 x1 = min(x,xx);x2 = max(x,xx); 64 y1 = min(y,yy); y2 = max(y,yy); 65 66 int ans=0; 67 ans += sum(x1-1,y1-1); 68 ans -= sum(x1-1,y2); 69 ans -= sum(x2,y1-1); 70 ans += sum(x2,y2); 71 printf("%d\n",ans); 72 } 73 74 if(cmd == 'A'){ 75 int x1,y1,n1; 76 scanf("%d%d%d%*c",&x1,&y1,&n1); 77 x1++;y1++; 78 a[x1][y1]+=n1; 79 add(x1,y1,n1); 80 } 81 if(cmd == 'D'){ 82 int x1,y1,n1; 83 scanf("%d%d%d%*c",&x1,&y1,&n1); 84 x1++;y1++; 85 n1 = min(n1,a[x1][y1]); 86 a[x1][y1]-=n1; 87 add(x1,y1,-n1); 88 } 89 if(cmd == 'M'){ 90 int x1,y1,x2,y2,n1; 91 scanf("%d%d%d%d%d%*c",&x1,&y1,&x2,&y2,&n1); 92 x1++;y1++;x2++;y2++; 93 n1=min(n1,a[x1][y1]); 94 a[x1][y1]-=n1;a[x2][y2]+=n1; 95 add(x1,y1,-n1); 96 add(x2,y2,n1); 97 } 98 } 99 } 100 return 0; 101 }