Cod sursa(job #2908481)

Utilizator AndreiCroitoruAndrei Croitoru AndreiCroitoru Data 3 iunie 2022 19:55:19
Problema Barbar Scor 100
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 2.85 kb
#include <bits/stdc++.h>

using namespace std;

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

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

int n, m;

pair<int, int> start, endd;
vector <vector<int> > mat;

bool ok(int i, int j)
{
    return i >= 0 && i < n&& j >= 0 && j < m && mat[i][j] == 0;
}

bool bfs(int minCost)
{
    queue<pair<int, int>> q;
    q.push({start.first, start.second});

    vector<vector<bool>> used(n, vector<bool>(m, 0));
    used[start.first][start.second] = 1;
    if (mat[start.first][start.second] < minCost)
        return false;

    while (!q.empty())
    {
        auto top = q.front();
        q.pop();
        for (int i = 0; i < 4; ++i)
        {
            int ni = top.first + di[i];
            int nj = top.second + dj[i];

            if (ni >= 0 && ni < n && nj >= 0 && nj < m)
            {
                if (mat[ni][nj] >= minCost && !used[ni][nj])
                {
                    if (ni == endd.first && nj == endd.second)
                        return true;

                    used[ni][nj] = 1;
                    q.push({ ni, nj });
                }
            }
        }
    }
    return false;
}

void sol()
{
    queue<pair<int, int>> q;
    for (int i = 0; i < n; i ++)
    {
        for (int j = 0; j < m; j ++)
        {
            if (mat[i][j] == -2)
            {
                q.push({ i, j });
            }
        }
    }
    while (!q.empty())
    {
        auto top = q.front();
        q.pop();

        for (int i = 0; i < 4; ++i)
        {
            int ni = top.first + di[i];
            int nj = top.second + dj[i];
            if (ok(ni, nj))
            {
                q.push({ni, nj});
                mat[ni][nj] = 1 + mat[top.first][top.second];
                if (mat[ni][nj] == -1)
                    mat[ni][nj] = 1;
            }
        }
    }

    int left = 0;
    int right = 10001;

    while (left <= right)
    {
        int mid = (left + right) / 2;

        if (!bfs(mid))
        {
            right = mid - 1;
        }
        else
        {
            left = mid + 1;
        }
    }

    out << right;
}



int main()
{

    in >> n >> m;
    mat.resize(n, vector<int>(m, 0));

    string linie;
    for (int i = 0; i < n; ++i)
    {
        in >> linie;
        for (int j = 0; j < linie.size(); ++j)
        {
            if (linie[j] == 'I')
            {
                start = { i, j };
            }
            else if (linie[j] == 'O')
            {
                endd = { i, j };
            }
            else if (linie[j] == '*')
            {
                mat[i][j] = -1;
            }
            else if (linie[j] == 'D')
            {
                mat[i][j] = -2;
            }
        }
    }
    sol();
    return 0;
}