[BZOJ3132] 上帝造题的七分钟

传送门

http://www.lydsy.com/JudgeOnline/problem.php?id=3132

题目大意

支持矩阵加减+矩阵和查询

题解

二维树状数组

const
    maxn=2048;
type
    data=array[0..maxn,0..maxn]of longint;
var
    c,d,e,f:data;
    i,j,k:longint;
    n,m,x1,x2,y1,y2,val,ans:longint;
    cha:char;
function query(var a:data;i,j:longint):longint;
var sum,tt:longint;
begin
    sum:=0; tt:=j;
    while i>0 do
        begin
            j:=tt;
            while j>0 do
                begin
                    inc(sum,a[i,j]);
                    dec(j,j and (-j));
                end;
            dec(i,i and (-i));
        end;
    exit(sum);
end;

function getsum(x,y:longint):longint;
var sum:longint;
begin
    sum:=(x+1)*(y+1)*query(c,x,y)-(x+1)*query(e,x,y)-(y+1)*query(d,x,y)+query(f,x,y);
    exit(sum);
end;

procedure update(var a:data;i,j,val:longint);
var tt:longint;
begin
    tt:=j;
    while i<=n do
        begin
            j:=tt;
            while j<=m do
                begin
                    inc(a[i,j],val);
                    inc(j,j and (-j));
                end;
            inc(i,i and (-i));
        end;
end;

begin
    readln(cha,n,m);
    fillchar(c,sizeof(c),0);
    fillchar(d,sizeof(d),0);
    fillchar(e,sizeof(e),0);
    fillchar(f,sizeof(f),0);
    while not eof do
        begin
            read(cha);
            if cha='k'
            then
                begin
                    readln(x1,y1,x2,y2);
                    ans:=getsum(x2,y2)-getsum(x1-1,y2)-getsum(x2,y1-1)+getsum(x1-1,y1-1);
                    writeln(ans);
                end
            else
                begin
                    readln(x1,y1,x2,y2,val);
                    update(c,x1,y1,val); update(c,x2+1,y1,-val); update(c,x1,y2+1,-val); update(c,x2+1,y2+1,val);
                    update(d,x1,y1,val*x1); update(d,x2+1,y1,-val*(x2+1)); update(d,x1,y2+1,-val*x1); update(d,x2+1,y2+1,val*(x2+1));
                    update(e,x1,y1,val*y1); update(e,x2+1,y1,-val*y1); update(e,x1,y2+1,-val*(y2+1)); update(e,x2+1,y2+1,val*(y2+1));
                    update(f,x1,y1,val*x1*y1); update(f,x2+1,y1,-val*(x2+1)*y1); update(f,x1,y2+1,-val*x1*(y2+1)); update(f,x2+1,y2+1,val*(x2+1)*(y2+1));
                end;
        end;
end.

你可能感兴趣的:([BZOJ3132] 上帝造题的七分钟)