Cod sursa(job #3312063)

Utilizator batasAndrei Batis batas Data 25 septembrie 2025 19:55:04
Problema Barbar Scor 80
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 3.06 kb
#include <iostream>
#include <iomanip>
#include <fstream>
#include <vector>
#include <queue>
#include <tuple>
#include <cstring>
#define iv (i + di[d])
#define jv (j + dj[d])
using namespace std;
using PI = pair<int, int>;
using VI = vector<int>;
using VVI = vector<VI>;

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

const int INF = 0x3f3f3f3f, DIM = 1005,
          di[] = {-1, 0, 1, 0},
          dj[] = {0, 1, 0, -1};

int n, m;
int ip, jp, is, js;
VVI c, drg;
queue<PI> Q;
char a[DIM][DIM];

void GetData();
void LeeDragon(int i, int j, VVI& c);
void LeePaftenie(int i, int j, int ceil, VVI& c);
int CautareBinara();
bool Check(int i, int j);
bool Ok(int val);
void Debug(VVI c);

int main()
{
    GetData();

    fout << CautareBinara();

    return 0;
}

int CautareBinara()
{
    int st(1), dr(1e6), mij, rez(-1);

    while (st <= dr)
    {
        mij = (st + dr) / 2;

        //fout << mij << '\n';

        if (Ok(mij))
        {
            rez = mij;
            st = mij + 1;
        }
        else
            dr = mij - 1;
    }

    return rez;
}

bool Ok(int val)
{
    LeePaftenie(ip, jp, val, c);

    if (c[is][js] != INF)
        return true;

    return false;
}

void LeeDragon(int i, int j, VVI& c)
{
    c[i][j] = 1;
    Q.emplace(i, j);

    while (!Q.empty())
    {
        tie(i, j) = Q.front();
        Q.pop();

        for (int d = 0; d < 4; ++d)
            if (Check(iv, jv) && c[iv][jv] > c[i][j] + 1)
            {
                c[iv][jv] = c[i][j] + 1;
                Q.emplace(iv, jv);
            }
    }
}

void LeePaftenie(int i, int j, int ceil, VVI& c)
{
    for (int i = 1; i <= n; ++i)
        for (int j = 1; j <= m; ++j)
            c[i][j] = INF;

    c[i][j] = 1;
    Q.emplace(i, j);

    while (!Q.empty())
    {
        tie(i, j) = Q.front();
        Q.pop();

        for (int d = 0; d < 4; ++d)
            if (Check(iv, jv) && drg[i][j] > ceil && c[iv][jv] > c[i][j] + 1)
            {
                c[iv][jv] = c[i][j] + 1;
                Q.emplace(iv, jv);
            }
    }
}

bool Check(int i, int j)
{
    if (i < 1 || i > n || j < 1 || j > m)
        return false;
    if (a[i][j] == '*')
        return false;

    return true;
}

void GetData()
{
    fin >> n >> m;

    c = VVI(n + 1, VI(m + 1, INF));
    drg = VVI(n + 1, VI(m + 1, INF));

    for (int i = 1; i <= n; ++i)
        for (int j = 1; j <= m; ++j)
        {
            fin >> a[i][j];

            if (a[i][j] == 'I')
                ip = i, jp = j;
            if (a[i][j] == 'O')
                is = i, js = j;
        }

    for (int i = 1; i <= n; ++i)
        for (int j = 1; j <= m; ++j)
            if (a[i][j] == 'D')
                LeeDragon(i, j, drg);
}

void Debug(VVI c)
{
    for (int i = 1; i <= n; ++i, fout << '\n')
        for (int j = 1; j <= m; ++j)
            if (c[i][j] == INF)
                fout << setw(3) << 0 << ' ';
            else
                fout << setw(3) << c[i][j] << ' ';
}