poj 2155

二维树状数组,区间更新,单点查询。。

树状数组中的
两个函数 Update()修改某个点的值(准确说是某个路径, 递增或递 减),Getsum()
求和区间(1, x)内的点的值。

修改某点 x 和求和某个区间(1, x)是可以互相调
换的,即我们可以用 Getsum(x, c)修改(1, x)这个区间内的点的值,而用
Update(x)来求该点的值。

我们要使区间(a, b)内的点 + c,只需要使区间(1, b)
内的点+c,而区间(1, a-1)内的点-c 即可。如果是二维的,修改矩阵(x1, y1)
到(x2, y2),即(x2, y2)+c, (x1-1,y2)-c, (x2, y1-1)-c, (x1-1,y1-1)+c 即
可。

#include<cstdio>
#include<cstring>

#define MAXN 1005
#define for if(0);else for

int c[MAXN][MAXN];
int N;

int lowbit(int x){
	return x&(-x);
}

void update(int i,int j,int v){
	for(int x=i;x<=N;x+=lowbit(x)){
		for(int y=j;y<=N;y+=lowbit(y)){
			c[x][y]+=v;
		}
	}
}

int getsum(int i,int j){
	int sum=0;
	for(int x=i;x>0;x-=lowbit(x)){
		for(int y=j;y>0;y-=lowbit(y)){
			sum+=c[x][y];
		}
	}
	return sum;
}

int main(){
	int t,m;
	int first=1;
	scanf("%d",&t);		
	while(t--){
		if(first)first=0;
		else puts("");
		char cmd;
		int x1,y1,x2,y2;
		scanf("%d%d",&N,&m);
		memset(c,0,sizeof(c));
		while(m--){
			scanf(" %c",&cmd);
			if(cmd=='C'){
				scanf("%d%d%d%d",&x1,&y1,&x2,&y2);
				update(x1,y1,1);
				update(x1,y2+1,-1);
				update(x2+1,y1,-1);
				update(x2+1,y2+1,1);
			}
			else {
				scanf("%d%d",&x1,&y1);
				int ans=getsum(x1,y1);
				if(ans&1)puts("1");
				else puts("0");
			}
		}
	}
}


 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值