HDU_2642_Stars

假设flag[i][j]=1表示灯亮,flag[i][j]=0表示灯灭

只有两种情况需要更新树状数组:

1、flag[x1][y1]=1,命令是D,add(x1,y1,1)

2、flag[x1][y1]=0,命令是B,add(x1,y1,-1)

由于树状数组的下标从1开始,而x1,y1有可能等于0,所以自增1

#include<iostream>

#include<cstdio>

#include<cstring>

#include<cmath>

#include<algorithm>

#include<string>

#include<queue>

using namespace std;

#define N 1005

int C[N][N]; //定义的全局变量,一开头初始值都是0

bool flag[N][N];

int sum(int x,int y) //x是横坐标,y是纵坐标

{

    int ret=0,i,j;

    for(i=x;i>0;i-=(i&-i))

        for(j=y;j>0;j-=(j&-j))

            ret+=C[i][j];

    return ret;

}

void add(int x,int y,int d) //d是需要增加的值

{

    int i,j;

   for(i=x;i<N;i+=(i&-i))

       for(j=y;j<N;j+=(j&-j))

           C[i][j]+=d;

}

int main()

{

 int t,a,b,c,d;

 char ask[5];

 scanf("%d",&t);

 while(t--)

 {

     scanf("%s",ask);

     if(ask[0]=='B')

     {

         scanf("%d%d",&a,&b);

         if(!flag[a+1][b+1])

         {

             flag[a+1][b+1]=1;

             add(a+1,b+1,1);

         }

     }

     else if(ask[0]=='D')

     {

         scanf("%d%d",&a,&b);

         if(flag[a+1][b+1])

         {

             flag[a+1][b+1]=0;

             add(a+1,b+1,-1);

         }

     }

     else{

         scanf("%d%d%d%d",&a,&b,&c,&d); //略坑,没有看清题目,前面两个是两个点的横坐标

         if(a>b) swap(a,b);

         if(c>d) swap(c,d);

         printf("%d\n",sum(b+1,d+1)-sum(b+1,c)-sum(a,d+1)+sum(a,c));

     }

 }

 return 0;

}

 

 

你可能感兴趣的:(tar)