Cod sursa(job #1938725)

Utilizator Burbon13Burbon13 Burbon13 Data 25 martie 2017 09:32:22
Problema Matrice 2 Scor 20
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.59 kb
#include <cstdio>
#include <algorithm>

using namespace std;

const int nmx = 302;
const int p1[] = {0,0,1,-1}, p2[] = {1,-1,0,0};

struct nod
{
    int i,j;
} v[nmx*nmx];

int n,m,mat[nmx][nmx];
int tata[nmx*nmx],rang[nmx*nmx];

struct Cmp
{
    bool operator() (nod n1, nod n2)
    {
        return mat[n1.i][n1.j] > mat[n2.i][n2.j];
    }
} cmp;

int poz(int i, int j)
{
    return (i - 1) * n + j;
}

void citire()
{
    scanf("%d %d", &n, &m);
    for(int i = 1; i <= n; ++i)
        for(int j = 1; j <= n; ++j)
        {
            scanf("%d", &mat[i][j]);
            int p = poz(i,j);
            v[p].i = i;
            v[p].j = j;
        }
}

void reset_paduri()
{
    for(int i = 1; i <= n * n; ++i)
    {
        tata[i] = i;
        rang[i] = 1;
    }
}

int da_grupa(int ni)
{
    int naux = ni;
    while(tata[naux] != naux)
        naux = tata[naux];
    int naux2;
    while(ni != tata[ni])
    {
        naux2 = tata[ni];
        tata[ni] = naux;
        ni = naux2;
    }
    return naux;
}

void uneste(int n1, int n2)
{
    if(rang[n1] > rang[n2])
        tata[n2] = n1;
    else
        tata[n1] = n2;
    if(rang[n1] == rang[n2])
        ++ rang[n2];
}

bool apartine(int i, int j)
{
    return i > 0 && i <= n && j > 0 && j <= n;
}

void uneste_val(int val)
{
    reset_paduri();
    int p = 1;
    while(mat[v[p].i][v[p].j] >= val)
    {
        for(int q = 0; q < 4; ++q)
            if(apartine(v[p].i+p1[q],v[p].j+p2[q]) && mat[v[p].i+p1[q]][v[p].j+p2[q]] >= val)
            {
                int g1 = da_grupa(poz(v[p].i,v[p].j));
                int g2 = da_grupa(poz(v[p].i+p1[q],v[p].j+p2[q]));
                if(g1 != g2)
                    uneste(g1,g2);
            }
        ++p;
    }
}

void queries()
{
    while(m--)
    {
        int x1,y1,x2,y2;
        scanf("%d %d %d %d", &x1, &y1, &x2, &y2);

        int maxim = -1,st = 1, dr = mat[v[1].i][v[1].j];
        while(st <= dr)
        {
            int mij = (st + dr) / 2;
            uneste_val(mij);
            if(da_grupa(poz(x1,y1)) == da_grupa(poz(x2,y2)))
            {
                maxim = mij;
                st = mij + 1;
            }
            else
                dr = mij - 1;
        }
        printf("%d\n", maxim);
    }
}

int main()
{
    freopen("matrice2.in", "r", stdin);
    freopen("matrice2.out", "w", stdout);
    citire();
    sort(v+1,v+n*n+1,cmp);
    /**for(int i = 1; i < 26; ++i)
        printf("%d %d %d\n", v[i].i, v[i].j, mat[v[i].i][v[i].j]);**/
    queries();
    return 0;
}