POJ2155 - Matrix
题目大意
给定一个大小为N*N的矩阵,每个元素要么为0要么为1,刚开始时A[i][j]=0,(1<=i,j<=N)
每次给出矩阵的左下角坐标(x1,y1)和右上坐标(x2,y2),将矩阵中的所有数组取反,或者给出一个坐标(x,y),要求你查询A[x][y]的值是多少。
题解
查询一个点和修改一个区间,这刚好是树状数组的可以实现的功能
代码:
#include<iostream> #include<cstdio> #include<cstring> #define MAXN 1005 using namespace std; int c[MAXN][MAXN]; int n; int lowbit(int x) { return x&-x; } int sum(int x,int y) { int i,j,ret=0; for(i=x;i>0;i-=lowbit(i)) for(j=y;j>0;j-=lowbit(j)) ret+=c[i][j]; return ret; } void add(int x,int y,int d) { int i,j; for(i=x;i<=n;i+=lowbit(i)) for(j=y;j<=n;j+=lowbit(j)) c[i][j]+=d; } int main(void) { char ch; int m,T,x1,y1,x2,y2,ans; cin>>T; while(T--) { scanf("%d%d",&n,&m); memset(c,0,sizeof(c)); while(m--) { getchar(); scanf("%c",&ch); if(ch=='C') { scanf("%d%d%d%d",&x1,&y1,&x2,&y2); add(x1,y1,1); add(x2+1,y1,1); add(x1,y2+1,1); add(x2+1,y2+1,1); } else { scanf("%d%d",&x1,&y1); ans=sum(x1,y1)&1; printf("%d\n",ans); } } printf("\n"); } return 0; }