Cod sursa(job #1083552)

Utilizator tavi.belu1994FMI Belu Andrei Octavian tavi.belu1994 Data 16 ianuarie 2014 03:25:30
Problema Struti Scor 100
Compilator cpp Status done
Runda Teme Pregatire ACM Unibuc 2013 Marime 2.14 kb
#include <cstdio>
#include <cstring>
#define nmax 1001
FILE *f,*g;
using namespace std;

int n,m,p,x,y,a[nmax][nmax],minim[nmax][nmax],maxim[nmax][nmax];

int stmin,drmin,drmax,stmax,D[nmax],V[nmax],d[nmax],v[nmax],minn,nr;

int getmin(int k)
{
    while(d[stmin]<k)
        stmin++;
    return v[stmin];
}

void addmin(int k,int val)
{
    while(drmin>=stmin && v[drmin]>=val)
        drmin--;
    d[++drmin]=k;
    v[drmin]=val;
}

int getmax(int k)
{
    while(D[stmax]<k)
        stmax++;
    return V[stmax];
}

void addmax(int k,int val)
{
    while(drmax>=stmax && V[drmax]<=val)
        drmax--;
    D[++drmax]=k;V[drmax]=val;
}

void solve(int x,int y)
{
    int i,j,dif;
    for(i=1;i<=n;i++)
    {
        stmin=1;
        drmin=0;
        stmax=1;
        drmax=0;
        for(j=1;j<x;j++)
        {
            addmin(j,a[i][j]);
            addmax(j,a[i][j]);
        }
        for(j=1;j<=m-x+1;j++)
        {
            addmin(j+x-1,a[i][j+x-1]);
            addmax(j+x-1,a[i][j+x-1]);
            minim[j][i]=getmin(j);
            maxim[j][i]=getmax(j);
        }
    }
    for(i=1;i<=m-x+1;i++)
    {
        stmin=1;
        drmin=0;
        stmax=1;
        drmax=0;
        for(j=1;j<y;j++)
        {
            addmin(j,minim[i][j]);
            addmax(j,maxim[i][j]);
        }
        for(j=1;j<=n-y+1;j++)
        {
            addmin(j+y-1,minim[i][j+y-1]);
            addmax(j+y-1,maxim[i][j+y-1]);
            dif = getmax(j)-getmin(j);
            if(dif < minn)
            {
                minn = dif;
                nr = 1;
            }
            else
                if(dif == minn) nr++;
        }
    }
}

int main()
{
    f=fopen("struti.in","r");
    g=fopen("struti.out","w");
    fscanf(f,"%d %d %d",&n,&m,&p);
    for(int i=1 ; i<=n ; i++)
        for(int j=1 ; j<=m ; j++)
            fscanf(f,"%d",&a[i][j]);
    for(int i=1 ; i<=p ; i++)
    {
        fscanf(f,"%d %d",&x,&y);
        minn=10000;
        solve(x,y);
        if(x!=y) solve(y,x);
        fprintf(g,"%d %d\n",minn,nr);
    }
    fclose(f);
    fclose(g);
    return 0;
}