1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94
| #include <iostream> #include <cstdio> #include <cstring> #include <vector> #include <queue> #define MAX_N 500 #define MAX_M 400000 #define INF 2147483647 using namespace std; int n, m, s, t, id[20][20], ind, tot, num, pre[MAX_N+5], cnt; char map[20][20]; vector <int> G[MAX_N+5], exi; int dis[MAX_N+5][MAX_N+5]; bool vis[MAX_N+5]; int nxt[4][2] = {{0, 1}, {0, -1}, {1, 0}, {-1, 0}}; struct node {int v, c, nxt;} E[MAX_M+5]; void init() {cnt = 0; s = 0, t = n*m+1; memset(pre, -1, sizeof(pre));} void insert(int u, int v, int c) { E[cnt].v = v, E[cnt].c = c, E[cnt].nxt = pre[u], pre[u] = cnt++; E[cnt].v = u, E[cnt].c = 0, E[cnt].nxt = pre[v], pre[v] = cnt++; } char gc(int x) {return map[(x-1)/m][(x-1)%m];} void BFS(int beg, int k) { memset(vis, false, sizeof(vis)); for (int i = 1; i <= n*m; i++) dis[i][k] = INF; queue <int> que; dis[beg][k] = 0, que.push(beg), vis[beg] = true; while (!que.empty()) { int u = que.front(); que.pop(); for (int i = 0; i < G[u].size(); i++) { int v = G[u][i]; if (vis[v] || gc(v) != '.') continue; dis[v][k] = dis[u][k]+1, que.push(v), vis[v] = true; } } } int d[MAX_N+5]; bool BFS() { memset(d, -1, sizeof(d)); queue <int> que; que.push(s), d[s] = 0; while (!que.empty()) { int u = que.front(); que.pop(); for (int i = pre[u]; ~i; i = E[i].nxt) { int v = E[i].v; if (~d[v] || !E[i].c) continue; d[v] = d[u]+1, que.push(v); } } return ~d[t]; } int DFS(int u, int flow) { if (u == t) return flow; int ret = 0; for (int i = pre[u]; ~i; i = E[i].nxt) { int v = E[i].v, c = E[i].c; if (d[v] != d[u]+1 || !c) continue; int tmp = DFS(v, min(flow, c)); E[i].c -= tmp, E[i^1].c += tmp, flow -= tmp, ret += tmp; if (!flow) break; } if (!ret) d[u] = -1; return ret; } bool check(int tans) { init(); for (int i = 0; i < n; i++) for (int j = 0; j < m; j++) if (map[i][j] == '.') insert(s, id[i][j], 1); for (int k = 0; k < exi.size(); k++) insert(exi[k], t, tans); for (int i = 0; i < n; i++) for (int j = 0; j < m; j++) if (map[i][j] == '.') for (int k = 0; k < exi.size(); k++) if (dis[id[i][j]][k] <= tans) insert(id[i][j], exi[k], 1); int ret = 0; while (BFS()) ret += DFS(s, INF); return ret == num; } int bi_search(int l, int r) { int ret; while (l <= r) { int mid = l+r>>1; if (check(mid)) ret = mid, r = mid-1; else l = mid+1; } return ret; } int main() { scanf("%d%d", &n, &m); for (int i = 0; i < n; i++) for (int j = 0; j < m; j++) id[i][j] = ++ind; for (int i = 0; i < n; i++) scanf("%s", map[i]); for (int i = 0; i < n; i++) for (int j = 0; j < m; j++) for (int k = 0; k < 4; k++) { int x = i+nxt[k][0], y = j+nxt[k][1]; if (x < 0 || x >= n || y < 0 || y >= m || map[i][j] == 'X' || map[x][y] == 'X') continue; G[id[i][j]].push_back(id[x][y]); } for (int i = 0; i < n; i++) for (int j = 0; j < m; j++) if (map[i][j] == '.') num++; for (int i = 0; i < n; i++) for (int j = 0; j < m; j++) if (map[i][j] == 'D') exi.push_back(id[i][j]); for (int i = 0; i < exi.size(); i++) BFS(exi[i], i); int ans = bi_search(0, m*n); if (ans < m*n) printf("%d", ans); else printf("impossible"); return 0; }
|