Pagini recente » Cod sursa (job #1552294) | Cod sursa (job #1220897) | Cod sursa (job #137914) | Cod sursa (job #361816) | Cod sursa (job #3308586)
#include <fstream>
#include <queue>
#include <cstring>
using namespace std;
ifstream cin("barbar.in");
ofstream cout("barbar.out");
int mat[1001][1001];
int way[1001][1001] = {0};
const int dx[] = {-1, 0, 1, 0}, dy[] = {0, 1, 0, -1};
int n, m;
int x_in, y_in, x_out, y_out;
int max_k = -1;
/*
. = -1
D = 0
* = -2
*/
queue<pair<int, int>> q;
inline bool inside(int i, int j) {
return i >= 1 && j >= 1 && i <= n && j <= m;
}
void lee() {
while (!q.empty()) {
int x = q.front().first, y = q.front().second;
q.pop();
for (int k = 0 ; k < 4 ; ++k) {
int nx = x + dx[k], ny = y + dy[k];
if (inside(nx, ny) && mat[nx][ny] == -1) {
mat[nx][ny] = mat[x][y] + 1;
q.push({nx, ny});
if (mat[nx][ny] > max_k) max_k = mat[nx][ny];
}
}
}
}
void drum(int distance) {
q.push({x_in, y_in});
way[x_in][y_in] = 1;
if (mat[x_in][y_in] < distance) return;
while (!q.empty()) {
int x = q.front().first, y = q.front().second;
q.pop();
for (int k = 0 ; k < 4 ; ++k) {
int nx = x + dx[k], ny = y + dy[k];
if (inside(nx, ny) && mat[nx][ny] >= distance && way[nx][ny] == 0) {
way[nx][ny] = way[x][y] + 1;
q.push({nx, ny});
}
}
}
}
int main() {
cin >> n >> m;
for (int i = 1 ; i <= n ; ++i) {
for (int j = 1 ; j <= m ; ++j) {
char c;
cin >> c;
if (c == '.') mat[i][j] = -1;
if (c == 'D') {
mat[i][j] = 0;
q.push({i, j});
}
if (c == '*') mat[i][j] = -2;
if (c == 'I') {
x_in = i; y_in = j;
mat[i][j] = -1;
}
if (c == 'O') {
x_out = i; y_out = j;
mat[i][j] = -1;
}
}
}
// lee multisource dragoni
lee();
int st = 0, dr = max_k;
int ans = - 1;
while (st <= dr) {
int mj = (st + dr) / 2;
drum(mj);
if (way[x_out][y_out] != 0) {
st = mj + 1;
ans = mj;
}
else dr = mj - 1;
memset(way, 0, sizeof(way));
}
cout << ans;
return 0;
}