Cod sursa(job #18798)

Utilizator sandyxpSanduleac Dan sandyxp Data 18 februarie 2007 14:07:34
Problema Plantatie Scor 10
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.04 kb
#include <cstdio>
#include <algorithm>
using std::max;

#define FIN "plantatie.in"
#define FOUT "plantatie.out"
#define MAXN 501
#define Lung 100000

int B[Lung];

int n, m;
int A[MAXN][MAXN];
int dx[] = { 0, 0, 1, 1 },
    dy[] = { 0, 1, 0, 1 };
int Qx, Qy, Ql;

int findmax(int poz, short x1, short y1, short x2, short y2)
{
    short i; int m=0, midx, midy;
    if (x1==x2 && y1==y2) return A[x1][y1];
    midx = (x1 + x2) >> 1;
    midy = (y1 + y2) >> 1;
    
    poz = (poz << 2) + 1;
    for (i=0; i<4; ++i, ++poz)
        m = max( B[poz] = findmax(poz, dx[i] ? (midx+1) : x1, dy[i] ? (midy+1) : y1,
                    dx[i] ? x2 : midx, dy[i] ? y2 : midy), m);
    return m;
}

inline bool inclus(short x1, short y1, short x2, short y2)
{
    return x1 >= Qx && x2 < Qx+Ql && y1 >= Qy && y2 < Qy+Ql;
}

int interogare(int poz, short x1, short y1, short x2, short y2)
{
    short i; bool ok;
    int midx, midy,   m = 0;
    if (inclus(x1,y1,x2,y2))  return B[poz];
    if (x1 >= x2 && y1 >= y2) return m;
    midx = (x1+x2) >> 1;
    midy = (y1+y2) >> 1;

    poz = (poz << 2) + 1;
    for (i=0; i<4; ++i, ++poz)
    {
        ok = 0;
        switch (i) {
            case 0: if (midx >= Qx && midy >= Qy) ok=1;break;
            case 1: if (midx >= Qx && midy < Qy+Ql) ok=1;break;
            case 2: if (midx < Qx+Ql && midy >= Qy) ok=1;break;
            case 3: if (midx < Qx+Ql && midy < Qy+Ql) ok=1;break;
        }
        if (!ok) continue;
        m = max(m, interogare(poz,dx[i]?(midx+1):x1,dy[i]?(midy+1):y1,dx[i]?x2:midx,dy[i]?y2:midy));
    }
    return m;
}

void fixme()
{
    B[0] = findmax(0, 1, 1, n, n);
    //for (int i=0; i<100; ++i) fprintf(stderr,"%d ", B[i]);
    
    while (m--)
    {
        scanf("%d %d %d\n", &Qx, &Qy, &Ql);
        printf("%d\n", interogare(0, 1, 1, n, n));
    }
}

void citire()
{
    int i, j;
    freopen(FIN, "r", stdin);
    freopen(FOUT,"w",stdout);
    scanf("%d %d", &n, &m);
    for (i=1; i<=n; ++i)
        for (j=1; j<=n; ++j)
            scanf("%d", &A[i][j]);
}

int main()
{
    citire();
    fixme();
    return 0;
}