Pagini recente » Monitorul de evaluare | Cod sursa (job #2154705) | Borderou de evaluare (job #2751153) | Monitorul de evaluare | Cod sursa (job #3306756)
#include <bits/stdc++.h>
using namespace std;
static const int INF = 1'000'000'000;
int main() {
ios::sync_with_stdio(false);
cin.tie(nullptr);
ifstream fin("barbar.in");
ofstream fout("barbar.out");
int R, C;
fin >> R >> C;
vector<string> grid(R);
for (int i = 0; i < R; ++i) {
fin >> grid[i];
}
auto in_bounds = [&](int r, int c) {
return r >= 0 && r < R && c >= 0 && c < C;
};
const int dr[4] = {-1, 1, 0, 0};
const int dc[4] = {0, 0, -1, 1};
auto id = [&](int r, int c) { return r * C + c; };
vector<int> dist(R * C, INF);
vector<char> is_wall(R * C, 0);
queue<pair<int,int>> q;
int sr = -1, sc = -1, tr = -1, tc = -1;
for (int r = 0; r < R; ++r) {
for (int c = 0; c < C; ++c) {
char ch = grid[r][c];
if (ch == '*') {
is_wall[id(r,c)] = 1;
dist[id(r,c)] = -1;
} else if (ch == 'D') {
dist[id(r,c)] = 0;
q.emplace(r, c);
} else if (ch == 'I') {
sr = r; sc = c;
} else if (ch == 'O') {
tr = r; tc = c;
}
}
}
while (!q.empty()) {
auto [r, c] = q.front(); q.pop();
int dcur = dist[id(r,c)];
for (int k = 0; k < 4; ++k) {
int nr = r + dr[k], nc = c + dc[k];
if (!in_bounds(nr, nc)) continue;
int nid = id(nr, nc);
if (is_wall[nid]) continue;
if (dist[nid] > dcur + 1) {
dist[nid] = dcur + 1;
q.emplace(nr, nc);
}
}
}
auto can = [&](int T) -> bool {
if (sr == -1 || tr == -1) return false;
int sid = id(sr, sc);
int tid = id(tr, tc);
if (is_wall[sid] || is_wall[tid]) return false;
if (dist[sid] < T || dist[tid] < T) return false;
queue<int> qq;
vector<char> vis(R * C, 0);
qq.push(sid);
vis[sid] = 1;
while (!qq.empty()) {
int u = qq.front(); qq.pop();
if (u == tid) return true;
int ur = u / C, uc = u % C;
for (int k = 0; k < 4; ++k) {
int vr = ur + dr[k], vc = uc + dc[k];
if (!in_bounds(vr, vc)) continue;
int vid = id(vr, vc);
if (vis[vid]) continue;
if (is_wall[vid]) continue;
if (dist[vid] < T) continue;
vis[vid] = 1;
qq.push(vid);
}
}
return false;
};
if (!can(0)) {
fout << -1 << '\n';
return 0;
}
int lo = 0, hi = R * C;
while (lo < hi) {
int mid = lo + (hi - lo + 1) / 2;
if (can(mid)) lo = mid;
else hi = mid - 1;
}
fout << lo << '\n';
return 0;
}