Cod sursa(job #2657730)

Utilizator loraclorac lorac lorac Data 11 octombrie 2020 20:03:43
Problema Matrice 2 Scor 100
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 2.35 kb
#include <bits/stdc++.h>
using namespace std;
ifstream in("matrice2.in");
ofstream out("matrice2.out");
const int lim1=305;
const int lim2=9e4+5;
vector<pair<int,int> > s;
int mat[lim1][lim1];
int v[lim2],cnt;
bool rev(pair<int,int> p1,pair<int,int> p2)
{
    return p1>p2;
}
int link[lim2];
int dim[lim2];
int tata(int x)
{
    int cpy=x,aux;
    while(x!=link[x]) x=link[x];
    while(cpy!=link[cpy]) aux=cpy,cpy=link[cpy],link[aux]=x;
    return x;
}
pair<int,int> papa[lim2];
vector<int> fii[lim2];
int nivel[lim2];
void unite(int x,int y,int lat)
{
    x=tata(x);
    y=tata(y);
    if(x==y) return;
    if(dim[x]<dim[y]) swap(x,y);
    fii[x].push_back(y);
    papa[y]={x,lat};
    dim[x]+=dim[y];
    link[y]=x;
}
void df(int nod)
{
    for(int x:fii[nod])
    {
        nivel[x]=nivel[nod]+1;
        df(x);
    }
}
const int dx[]={1,0,-1,0};
const int dy[]={0,1,0,-1};
bool interior(int x,int y,int n)
{
    if(1<=x and x<=n and 1<=y and y<=n)
        return true;
    return false;
}
bool consider[lim1][lim1];
int root;
void build(int n)
{
    sort(s.begin(),s.end(),rev);
    for(pair<int,int> p:s)
    {
        int val=p.first;
        int x=(p.second-1)/n+1;
        int y=(p.second-1)%n+1;
        consider[x][y]=1;
        for(int d=0;d<4;++d)
        {
            int xx=x+dx[d];
            int yy=y+dy[d];
            if(interior(xx,yy,n) and consider[xx][yy])
                unite(p.second,mat[xx][yy],val);
        }
    }
    root=tata(1);
    df(root);
}
int main()
{
    int n,q,x1,y1,x2,y2;
    in>>n>>q;
    for(int i=1;i<=n;++i)
    for(int j=1;j<=n;++j)
    {
        ++cnt;
        in>>v[cnt];
        link[cnt]=cnt;
        dim[cnt]=1;
        s.push_back({v[cnt],cnt});
        mat[i][j]=cnt;
    }
    build(n);
    while(q--)
    {
        in>>x1>>y1>>x2>>y2;
        int a=mat[x1][y1];
        int b=mat[x2][y2];
        int la=v[a],lb=v[b];
        while(a!=b)
        {
            if(nivel[a]<nivel[b])
                lb=min(lb,papa[b].second),b=papa[b].first;
            else if(nivel[a]>nivel[b])
                la=min(la,papa[a].second),a=papa[a].first;
            else
                la=min(la,papa[a].second),lb=min(lb,papa[b].second),
                a=papa[a].first,b=papa[b].first;
        }
        out<<min(la,lb)<<'\n';
    }
    return 0;
}