Question:
There are K milking stations and C cows. Each milking station can only serve a maximum of M cows every day. There is a distance between the cows and the milking station, in the matching scheme that can be milked for all the cows in a day, select the farthest distance and minimum scheme.
Solution:
The edge relationship is constructed by means of bipartite enumeration, and then the network flow is used to determine whether all the cows can be milked when the conditions are met.
The Code is as follows:
# Include <cstdlib> # include <cstring> # include <cstdio> # include <algorithm> # define INF 0x3fffffffusing namespace STD; int K, C, M, idx; int G [250] [250], head [250], Ss = 240, TT = 241; int dis [250], que [250], front, tail; struct node {int V, next, cap;} e [60000]; void Floyd () {for (int K = 1; k <= K + C; ++ K) {for (INT I = 1; I <= K + C; ++ I) {for (Int J = 1; j <= K + C; ++ J) {If (G [I] [k]! =-1 & G [k] [J]! =-1) {If (G [I] [k] + G [k] [J] <G [I] [J] | G [I] [J] =-1) {// If a point is-1, it should be directly updated, G [I] [J] = G [I] [k] + G [k] [J] ;}}} /* For (INT I = k + 1; I <= K + C; ++ I) {for (Int J = 1; j <= K; ++ J) {printf ("% d = % d \ n", I, j, G [I] [J]) ;}} system ("pause "); */} void addedge (int x, int V, int cap) {++ idx; E [idx]. V = V, E [idx]. CAP = CAP; E [idx]. next = head [X]; head [x] = idx;} bool BFS () {int Pos; memse T (DIS, 0xff, sizeof (DIS); DIS [ss] = 0; front = tail = 0; que [++ tail] = SS; while (front! = Tail) {pos = que [++ front]; for (INT I = head [POS]; I! =-1; I = E [I]. next) {int v = E [I]. v, Cap = E [I]. CAP; If (DIS [v] =-1 & Cap> 0) {dis [v] = dis [POS] + 1; que [++ tail] = V ;}} return dis [TT]! =-1;} int DFS (int u, int flow) {If (u = TT) {return flow;} int TF = 0, F; for (INT I = head [u]; I! =-1; I = E [I]. next) {int v = E [I]. v, Cap = E [I]. CAP; If (DIS [v] = dis [u] + 1 & Cap> 0 & (F = DFS (v, min (Cap, flow )))) {e [I]. cap-= F, E [I ^ 1]. cap + = f; flow-= f; TF + = f;} If (tf = 0) dis [u] =-1; return TF;} int dinic () {int ret = 0; while (BFS () {RET + = DFS (SS, INF);} return ret;} int bsearch (int l, int R) {int ret; while (L <= r) {int mid = (L + r)> 1; memset (Head, 0xff, sizeof (H EAD); idx =-1; for (INT I = 1; I <= K; ++ I) {// traverses all the milking runners addedge (I, TT, m); // The edge capacity is its maximum limit addedge (TT, I, 0);} For (INT I = k + 1; I <= K + C; ++ I) {// traverse all the cows addedge (SS, I, 1); addedge (I, SS, 0); For (Int J = 1; j <= K; ++ J) {// enumerative the distance from each cow to the milking machine if (G [I] [J]! =-1 & G [I] [J] <= mid) {addedge (I, j, 1); addedge (J, I, 0 );}}} if (dinic () = c) {ret = mid; r = mid-1 ;}else {L = Mid + 1 ;}} return ret ;}int main () {While (scanf ("% d", & K, & C, & M) = 3) {// The first K are milking stations, location of the next C cows: memset (G, 0xff, sizeof (g); For (INT I = 1; I <= K + C; ++ I) {for (Int J = 1; j <= K + C; ++ J) {scanf ("% d", & G [I] [J]); if (G [I] [J] = 0) g [I] [J] =-1 ;}} Floyd (); // The right boundary is not 200, because some edges may pass the previous printf ("% d \ n", bsearch (1, 50000);} return 0;} through other edges ;}