Cod sursa(job #3189452)

Utilizator AndreiBOTOBotocan Andrei AndreiBOTO Data 5 ianuarie 2024 14:49:59
Problema Matrice 2 Scor 100
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 2.83 kb
#include <bits/stdc++.h>

#pragma optimize GCC ("Ofast")
#pragma GCC optimize("O3")
#pragma GCC optimize("unroll-loops")

///#include <tryhardmode>
///#include <GODMODE::ON>

using namespace std;

ifstream fin ("matrice2.in");
ofstream fout ("matrice2.out");

const int NMAX=305;
const int QMAX=2e4+5;

int di[]={-1,1,0,0};
int dj[]={0,0,-1,1};

int a[NMAX][NMAX];
bool viz[NMAX][NMAX];
int ans[QMAX];
int t[NMAX*NMAX];
int p[NMAX*NMAX];

int n;

struct elem{
    int x1;
    int x2;
    int y1;
    int y2;
    int ind;
    int rez;
}query[QMAX];

bool intmat(int a,int b)
{
    return a>=1 && b>=1 && a<=n && b<=n;
}

bool cmp(elem a,elem b)
{
    return a.rez>b.rez;
}

bool cmp2(pair<int,int>x,pair<int,int>y)
{
    return a[x.first][x.second]>a[y.first][y.second];
}

int get_line(int x,int y)
{
    return (x-1)*n+y;
}

int root(int x)
{
    if(t[x]==x)
        return x;
    return t[x]=root(t[x]);
}

void solve(int x,int y)
{
    x=root(x);
    y=root(y);
    if(x==y)
        return ;
    if(p[x]>p[y])
        swap(x,y);
    t[y]=x;
    p[x]+=p[y];
}

void reset()
{
    int i,j;
    for(i=1;i<=n;i++)
    {
        for(j=1;j<=n;j++)
        {
            int aux=get_line(i,j);
            t[aux]=aux;
            p[aux]=1;
            viz[i][j]=false;
        }
    }
}

int main()
{
    ios_base::sync_with_stdio(false);
    fin.tie(NULL);
    fout.tie(NULL);

    int q,i,j,step,curr=0,d;
    fin>>n>>q;

    for(i=1;i<=n;i++)
        for(j=1;j<=n;j++)
            fin>>a[i][j];
    for(i=1;i<=q;i++)
    {
        fin>>query[i].x1>>query[i].y1>>query[i].x2>>query[i].y2;
        query[i].ind=i;
        query[i].rez=1;
    }
    vector<pair<int,int>>v;
    for(i=1;i<=n;i++)
        for(j=1;j<=n;j++)
            v.push_back(make_pair(i,j));
    sort(v.begin(),v.end(),cmp2);
    for(step=(1<<19);step>0;step>>=1)
    {
        sort(query+1,query+q+1,cmp);
        reset();
        curr=0;
        for(i=1;i<=q;i++)
        {
            while(curr<v.size() && query[i].rez+step<=a[v[curr].first][v[curr].second])
            {
                viz[v[curr].first][v[curr].second]=true;
                for(d=0;d<4;d++)
                {
                    int ii=v[curr].first+di[d];
                    int jj=v[curr].second+dj[d];
                    if(intmat(ii,jj) && viz[ii][jj])
                        solve(get_line(ii,jj),get_line(v[curr].first,v[curr].second));
                }
                curr++;
            }
            if(root(get_line(query[i].x1,query[i].y1))==root(get_line(query[i].x2,query[i].y2)))
                query[i].rez+=step;
        }
    }
    for(i=1;i<=q;i++)
        ans[query[i].ind]=query[i].rez;
    for(i=1;i<=q;i++)
        fout<<ans[i]<<"\n";
    fin.close();
    fout.close();
    return 0;
}