POJ 1195 Mobile phones (树状数组)

题意:给定n*n矩阵,和几种在线操作,包括对某一点(x,y)值修改,查询一个矩形(x1,y1,x2,y2)的元素和。

思路:典型的在线查询,可用树状数组实现,查询矩形和时,稍微注意以下就可以了:

  sum(x2,y2)+sum(x1-1,y1-1)-sum(x1-1,y2)-sum(x2,y1-1);

还要注意树状数组的修改操作modify(index,delta)中的index要>0。

 

  
    
#include < iostream >
#include
< cstdio >
#include
< algorithm >
#include
< memory.h >
#include
< cmath >
#include
< bitset >
#include
< queue >
#include
< vector >
using namespace std;

const int BORDER = ( 1 << 20 ) - 1 ;
const int MAXSIZE = 37 ;
const int MAXN = 1100 ;
const int INF = 1000000000 ;
#define CLR(x,y) memset(x,y,sizeof(x))
#define ADD(x) x=((x+1)&BORDER)
#define IN(x) scanf("%d",&x)
#define OUT(x) printf("%d\n",x)
#define MIN(m,v) (m)<(v)?(m):(v)
#define MAX(m,v) (m)>(v)?(m):(v)
#define ABS(x) ((x)>0?(x):-(x))

int tre[MAXN][MAXN];
int n,n_tre,t_case;

int lowbit( int x)
{
return x & ( - x);
}
void modify( const int & x, const int & y, const int delta)
{
for ( int i = x; i <= n_tre; i += lowbit(i))
for ( int j = y; j <= n_tre; j += lowbit(j))
{
tre[i][j]
+= delta;
}
}
int get_sum( const int & x, const int & y)
{
int sum = 0 ;
for ( int i = x; i > 0 ; i -= lowbit(i))
for ( int j = y; j > 0 ; j -= lowbit(j))
sum
+= tre[i][j];
return sum;
}
int init()
{
CLR(tre,
0 );
return 0 ;
}
int work()
{
int i,j,x1,x2,y1,y2,x,y,val,tmp,ans;
char s[ 3 ];
n_tre
= n + 5 ;
while (scanf( " %s " ,s))
{
if (s[ 0 ] == ' 3 ' )
break ;
if (s[ 0 ] == ' 1 ' )
{
scanf(
" %d%d%d " , & x, & y, & val);
modify(x
+ 1 ,y + 1 ,val);
}
else
{
scanf(
" %d%d%d%d " , & x1, & y1, & x2, & y2);
ans
= get_sum(x2 + 1 ,y2 + 1 ) + get_sum(x1,y1) -
get_sum(x1,y2
+ 1 ) - get_sum(x2 + 1 ,y1);
OUT(ans);
}
}
return 0 ;
}
int main()
{
while (scanf( " %d %d " , & t_case, & n) != EOF)
{
init();
work();
}
return 0 ;
}

 

 

你可能感兴趣的:(mobile)