Started on hrbust, the data is changed to 20, and the matrix and the normal maximum stream are used.AlgorithmYes! Later, I found that the data on HDU is much larger than that, and the number of points can reach up to 40000. For the first time, MLE is replaced with an adjacent table, and the second TLE is replaced with an algorithm. SAP is easy to use!
The method for creating a graph is to connect 2 at a long distance, 1 at the end, and INF at the capacity. connect each cell to the grid. The capacity is 1 and the minimum cut is required! Here, the minimum cut is very easy to understand. It is like walking from 2 to 1, and then passing through the boundary of a grid every time, no matter how many wolves pass through this boundary, you only need one fence, that is, each boundary has only one position to place the fence. Generally, there are three or four boundary. In this way, you can build a graph from all 2 S to 1 s. You only need to delete the vertices on the smallest cut to prevent connections between 1 s and 2 s!
Below isCode:
# Include <cstdio> # include <cstring> # include <algorithm> # include <queue> using namespace STD; const int maxn = 40010; const int maxm = 2000020; const int INF = 0x3fffffff; struct node {int to, next, cap;} edge [maxm]; // note that maxmint Tol, n, m; int head [maxn]; int gap [maxn], DIS [maxn], pre [maxn], cur [maxn]; void addedge (int u, int V, int W, int RW = 0) {edge [tol]. to = V; edge [tol]. CAP = W; edge [tol]. next = head [u]; head [u] = tol ++; edge [Tol ]. To = u; edge [tol]. CAP = RW; edge [tol]. next = head [v]; head [v] = tol ++;} int SAP (INT start, int end, int nodenum) {memset (DIS, 0, sizeof (DIS); memset (GAP, 0, sizeof (GAP); memcpy (cur, Head, sizeof (head); int u = pre [start] = start, maxflow = 0, Aug =-1; Gap [0] = nodenum; while (DIS [start] <nodenum) {loop: For (Int & I = cur [u]; i! =-1; I = edge [I]. next) {int v = edge [I]. to; If (edge [I]. cap & dis [u] = dis [v] + 1) {If (Aug =-1 | Aug> edge [I]. CAP) Aug = edge [I]. CAP; Pre [v] = u; u = V; If (V = END) {maxflow + = Aug; For (u = pre [u]; V! = Start; V = u, u = pre [u]) {edge [cur [u]. cap-= Aug; edge [cur [u] ^ 1]. cap + = Aug;} Aug =-1;} goto loop;} int mindis = nodenum; For (INT I = head [u]; I! =-1; I = edge [I]. next) {int v = edge [I]. to; If (edge [I]. cap & mindis> dis [v]) {cur [u] = I; mindis = dis [v] ;}} if (-- gap [dis [u]) = 0) break; Gap [dis [u] = mindis + 1] ++; u = pre [u];} return maxflow ;} int o [205] [205]; int main () {int icase = 1; while (scanf ("% d", & N, & M )! = EOF) {int S = 0, T = N * m + 1; Tol = 0; memset (Head,-1, sizeof (head )); for (INT I = 1; I <= N; ++ I) for (Int J = 1; j <= m; ++ J) {scanf ("% d ", & O [I] [J]); int u = (I-1) * m + J; If (O [I] [J] = 1) addedge (u, T, INF, 0); else if (O [I] [J] = 2) addedge (S, U, INF, 0); if (I> 1) addedge (u, u-m, 1, 0); if (I <n) addedge (u, u + M, 1, 0); If (j> 1) addedge (u, U-1, 1, 0); If (j <m) addedge (u, u + 1, 1, 0);} printf ("case % d: \ n % d \ n ", icase ++, SAP (s, t, t + 1 ));}}