Cod sursa(job #2296083)

Utilizator cahemanCasian Patrascanu caheman Data 4 decembrie 2018 12:40:37
Problema Barbar Scor 50
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 4.37 kb
#include<cstdio>
#include<queue>
#include<cstring>

using namespace std;

char mat[1005][1005];
int viz[1005][1005];
int dist[1005][1005];
queue <int> dragonasi, qc;

void solve(int i, int start)
{
    int curent, curentx, curenty;
    qc.push(start);
    while(!qc.empty())
        {
            curent  = qc.front();
            curentx = curent / 1001;
            curenty = curent % 1001;
            if(viz[curentx + 1][curenty] == 0 && mat[curentx + 1][curenty] != '*')
            {
                if(dist[curentx + 1][curenty] >= i)
                    qc.push(curent + 1001);
                viz[curentx + 1][curenty] = 1;
            }
            if(viz[curentx - 1][curenty] == 0 && mat[curentx - 1][curenty] != '*')
            {
                if(dist[curentx - 1][curenty] >= i)
                    qc.push(curent - 1001);
                viz[curentx - 1][curenty] = 1;
            }
            if(viz[curentx][curenty + 1] == 0 && mat[curentx][curenty + 1] != '*')
            {
                if(dist[curentx][curenty + 1] >= i)
                    qc.push(curent + 1);
                viz[curentx][curenty + 1] = 1;
            }
            if(viz[curentx][curenty - 1] == 0 && mat[curentx][curenty - 1] != '*')
            {
                if(dist[curentx][curenty - 1] >= i)
                    qc.push(curent - 1);
                viz[curentx][curenty - 1] = 1;
            }
            qc.pop();
        }
}

int main()
{
    freopen("barbar.in", "r", stdin);
    freopen("barbar.out", "w", stdout);
    int r, col, i, j, startx, starty, finishx, finishy, curent, curentx, curenty;
    scanf("%d%d\n", &r, &col);
    for(i = 1; i <= r; ++ i)
        scanf("%s", &mat[i]);
    for(i = 1; i <= r; ++ i)
        for(j = 1; j <= col; ++ j)
        {
            if(mat[i][j] == 'D')
            {
                dragonasi.push(i * 1001 + j);
                viz[i][j] = 1;
                mat[i][j] = '*';
            }
            if(mat[i][j] == 'I')
            {
                startx = i;
                starty = j;
            }
            if(mat[i][j] == 'O')
            {
                finishx = i;
                finishy = j;
            }
        }
    for(i = 0; i <= r + 1; ++ i)
        mat[i][0] = mat[i][col + 1] = '*';
    for(i = 0; i <= col + 1; ++ i)
        mat[0][i] = mat[r + 1][i] = '*';
    while(!(dragonasi.empty()))
    {
        curent = dragonasi.front();
        curentx = curent / 1001;
        curenty = curent % 1001;
        if(curentx < r)
        if(viz[curentx + 1][curenty] == 0)
           if(mat[curentx + 1][curenty] != '*')
        {
            dist[curentx + 1][curenty] = dist[curentx][curenty] + 1;
            dragonasi.push(curent + 1001);
            viz[curentx + 1][curenty] = 1;
        }
        if(curentx>1)
        if(viz[curentx - 1][curenty] == 0)
            if(mat[curentx - 1][curenty] != '*')
        {
            dist[curentx - 1][curenty] = dist[curentx][curenty] + 1;
            dragonasi.push(curent - 1001);
            viz[curentx - 1][curenty] = 1;
        }
        if(curenty<col)
        if(viz[curentx][curenty + 1] == 0)
        if(mat[curentx][curenty + 1] != '*')
        {
            dist[curentx][curenty + 1] = dist[curentx][curenty] + 1;
            dragonasi.push(curent + 1);
            viz[curentx][curenty + 1] = 1;
        }
        if(curenty > 1)
        if(viz[curentx][curenty - 1] == 0)
        if(mat[curentx][curenty - 1] != '*')
        {
            dist[curentx][curenty - 1] = dist[curentx][curenty] + 1;
            dragonasi.push(curent - 1);
            viz[curentx][curenty - 1] = 1;
        }
        dragonasi.pop();
    }
    for(i = 1; i <= r; ++ i)
        for(j = 1; j <= col; ++ j)
            viz[i][j] = 0;
    solve(1, startx * 1001 + starty);
    if(viz[finishx][finishy] == 0)
    {
        printf("-1");
        return 0;
    }
    int st, dr, med, last = 0;
    st = 1;
    dr = r * col;
    while(st <= dr)
    {
        med = (st + dr) / 2;
        for(i = 1; i <= r; ++ i)
            for(j = 1; j <= col; ++ j)
                viz[i][j] = 0;
        solve(med, startx * 1001 + starty);
        if(viz[finishx][finishy])
        {
            last = med;
            st = med + 1;
        }
        else
            dr = med - 1;
    }
    printf("%d", last);
    return 0;
}