Cod sursa(job #2766741)

Utilizator AlexZeuVasile Alexandru AlexZeu Data 3 august 2021 07:48:32
Problema Barbar Scor 90
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 2.96 kb
#include <bits/stdc++.h>
using namespace std;

const int mxN = 1e3 + 5, INF = 1e9 + 7;

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

int n, m, dist_barbar[mxN][mxN], dist_dragon_cell[mxN][mxN], finish_x, finish_y, start_x, start_y;
queue<pair<int, int>> dragons, barbar;

vector<pair<int, int>> directions = {{0, 1}, {0, -1}, {1, 0}, {-1, 0}};

bool valid(int x, int y) {
    return (x >= 1 && x <= n && y >= 1 && y <= m && dist_barbar[x][y] != -1);
}

void bfs_dragon() {
    while (dragons.size()) {
        int cell_x = dragons.front().first;
        int cell_y = dragons.front().second;
        dragons.pop();
        for (pair<int, int> dir : directions) {
            int new_x = cell_x + dir.first;
            int new_y = cell_y + dir.second;
            if (valid(new_x, new_y) && dist_dragon_cell[new_x][new_y] > dist_dragon_cell[cell_x][cell_y] + 1) {
                dist_dragon_cell[new_x][new_y] = dist_dragon_cell[cell_x][cell_y] + 1;
                dragons.push({new_x, new_y});
            }
        }
    }
}

void bfs_barbar() {
    barbar.push({start_x, start_y});
    dist_barbar[start_x][start_y] = dist_dragon_cell[start_x][start_y];
    while(barbar.size()) {
        int cell_x = barbar.front().first;
        int cell_y = barbar.front().second;
        barbar.pop();
        for (pair<int, int> dir : directions) {
            int new_x = cell_x + dir.first;
            int new_y = cell_y + dir.second;
            if (valid(new_x, new_y) && dist_barbar[new_x][new_y] < min(dist_barbar[cell_x][cell_y], dist_dragon_cell[new_x][new_y])) {
                dist_barbar[new_x][new_y] = min(dist_barbar[cell_x][cell_y], dist_dragon_cell[new_x][new_y]);
                barbar.push({new_x, new_y});
            }
        }
    }
}

void solve() {
    fin >> n >> m;
    for (int i = 1; i <= n; ++i) {
        for (int j = 1; j <= m; ++j) {
            char c;
            fin >> c;
            dist_barbar[i][j] = 0;
            dist_dragon_cell[i][j] = INF;
            if (c == 'I') {
                start_x = i;
                start_y = j;
            } else if (c== 'O') {
                finish_x = i;
                finish_y = j;
            } else if (c == 'D') {
                dist_dragon_cell[i][j] = 0;
                dragons.push({i, j});
                dist_barbar[i][j] = -1;
            } else if (c == '*'){
                dist_barbar[i][j] = -1;
            }
        }
    }
    bfs_dragon();
    bfs_barbar();
    fout << (dist_barbar[finish_x][finish_y] == 0 ? -1 : dist_barbar[finish_x][finish_y]);
}

int main() {
    fin.tie(0);fout.tie(0);
    ios::sync_with_stdio(false);
    int T = 1;
//    cin >> T;
    while (T--) {
        solve();
    }
    return 0;
}

//read the question correctly (ll vs int)
//what's the meaning of the problem ? Think outside the BOX !!!
//edge cases ?
//make it simple
//write everything (observations, edge cases, ideas, steps, methods, ...)