2012-05-12 17:53:37Morris
Segment Tree,二維線段樹版本,zkw式
[UVA] 11297 - Census
#include <stdio.h>#include <string.h>
#define max(x, y) ((x) > (y) ? (x) : (y))
#define min(x, y) ((x) < (y) ? (x) : (y))
struct subTree {
int maxv, minv;
};
struct segmentTree {
subTree subtree[1025];
} mainTree[1025];
int Mmain, Msub;
void subbuild(int k) {
int i;
for(i = 2*Msub-1; i > 0; i--) {
mainTree[k].subtree[i].maxv = 0;
mainTree[k].subtree[i].minv = 0;
}
}
void build() {
int i;
for(i = 2*Mmain; i > 0; i--) {
subbuild(i);
}
}
void submodify(int k, int y) {
static int s;
for(s = y+Msub; s > 0; s >>= 1) {
mainTree[k].subtree[s].maxv = max(mainTree[k<<1].subtree[s].maxv, mainTree[k<<1|1].subtree[s].maxv);
mainTree[k].subtree[s].minv = min(mainTree[k<<1].subtree[s].minv, mainTree[k<<1|1].subtree[s].minv);
}
}
void modify(int x, int y, int v) {
static int s, t;
mainTree[x+Mmain].subtree[y+Msub].maxv = v;
mainTree[x+Mmain].subtree[y+Msub].minv = v;
t = x+Mmain;
for(s = (y+Msub)>>1; s > 0; s >>= 1) {
mainTree[t].subtree[s].maxv = max(mainTree[t].subtree[s<<1].maxv, mainTree[t].subtree[s<<1|1].maxv);
mainTree[t].subtree[s].minv = min(mainTree[t].subtree[s<<1].minv, mainTree[t].subtree[s<<1|1].minv);
}
for(s = (x+Mmain)>>1; s > 0; s >>= 1) {
submodify(s, y);
}
}
int ansMax, ansMin;
void subquery(int k, int lc, int rc) {
static int s, t;
for(s = lc+Msub-1, t = rc+Msub+1; (s^t) != 1;) {
if(~s&1) {
ansMax = max(ansMax, mainTree[k].subtree[s^1].maxv);
ansMin = min(ansMin, mainTree[k].subtree[s^1].minv);
}
if(t&1) {
ansMax = max(ansMax, mainTree[k].subtree[t^1].maxv);
ansMin = min(ansMin, mainTree[k].subtree[t^1].minv);
}
s >>= 1, t >>= 1;
}
}
void query(int lr, int rr, int lc, int rc) {
static int s, t;
for(s = lr+Mmain-1, t = rr+Mmain+1; (s^t) != 1;) {
if(~s&1) {
subquery(s^1, lc, rc);
}
if(t&1) {
subquery(t^1, lc, rc);
}
s >>= 1, t >>= 1;
}
}
inline int ReadInt(int *x) {
static char c, neg;
while((c = getchar()) < '-') {if(c == EOF) return EOF;}
neg = (c == '-') ? -1 : 1;
*x = (neg == 1) ? c-'0' : 0;
while((c = getchar()) >= '0')
*x = (*x << 3) + (*x << 1) + c-'0';
*x *= neg;
return 1;
}
int main() {
int n, m, q, x, y, v;
int i, j, x1, x2, y1, y2;
while(scanf("%d %d", &n, &m) == 2) {
for(Mmain = 1; Mmain < n+2; Mmain <<= 1);
for(Msub = 1; Msub < m+2; Msub <<= 1);
build();
for(i = 1; i <= n; i++) {
for(j = 1; j <= m; j++) {
ReadInt(&x);
modify(i, j, x);
}
}
scanf("%d", &q);
getchar();
char cmd;
while(q--) {
cmd = getchar();
if(cmd == 'q') {
ReadInt(&x1), ReadInt(&y1), ReadInt(&x2), ReadInt(&y2);
ansMax = 0, ansMin = 0xfffffff;
query(x1, x2, y1, y2);
printf("%d %d\n", ansMax, ansMin);
} else {
ReadInt(&x), ReadInt(&y), ReadInt(&v);
modify(x, y, v);
}
}
}
return 0;
}