Poj 3436 ACM computer factory
Link: http://poj.org/problem? Id = 3436
Question:Each computer has P parts, which can be processed by different machines. There are n machines, each of which is described with 2 p + 1 integers: Qi Si, 1 Si, 2... si, P Di, 1 Di, 2... di, P, where Qi specifies the machine performance, indicating the number of computers processed per hour. Si and J are the Input specifications of section J. 0 indicates that this part cannot be processed. 1 indicates that this part must be processed. 2 indicates that both parts can be processed. Di, k is the output specification of the K part. 0 indicates that the part is not processed by the machine, and 1 indicates that the part is processed by the machine. 1 ≤ p ≤ 10, 1 ≤ n ≤ 50, 1 ≤ Qi ≤10000.
Ideas:Create a source point, as long as the s part of each machine is not 1, that is, from the source point to its edge, the traffic is the efficiency of the machine. Establish a settlement point. As long as the D part of each machine is 1, the traffic is the efficiency of the machine. If the output part of a machine matches the input part of a machine, the two are connected to the edge and the traffic is Min (QI, Qj ). If the input part of machine J is 2, the output part of machine I is random; otherwise, the output part of machine J must be the same as that of machine J.
PS:You can also split the question to separate the input and output parts of each machine, and connect the edge. The traffic is the efficiency of the machine. If the matching is performed between different machines, the traffic is INF. When the source and sink are connected to the machine, the traffic is also INF.
Code:
/* ID: [email protected] prog: Lang: c ++ */# include <map> # include <set> # include <queue> # include <stack> # include <cmath> # include <cstdio> # include <vector> # include <string> # include <fstream> # include <cstring> # include <ctype. h> # include <iostream> # include <algorithm> using namespace STD; # define linf (1ll <60) # define Inf (1 <30) # define PI ACOs (-1.0) # define MEM (a, B) memset (a, B, sizeof (A) # define rep (I, A, n) for (INT I = A; I <n; I ++) # define per (I, A, n) for (INT I = n-1; I> = A; I --) # define EPS 1e-6 # define debug puts ("================ ") # define Pb push_back // # define MP make_pair # define all (x ). begin (), (x ). end () # define Fi first # define se second # define SZ (x) (INT) (x ). size () # define posin (x, y) (0 <= (x) & (x) <n & 0 <= (y) & (y) <m) typedef long ll; typedef unsigned long ull; const int maxn = 60; c Onst int maxm = 20000; int St, Ed, N; int P, N; int s [maxn] [10], d [maxn] [10], Q [maxn]; struct node {int V; // vertex int cap; // capacity int flow; // current flow in this arc int NXT;} e [maxm * 2]; int G [maxn], CNT; void add (int u, int V, int c) {e [++ CNT]. V = V; E [CNT]. CAP = C; E [CNT]. flow = 0; E [CNT]. NXT = G [u]; G [u] = CNT; E [++ CNT]. V = u; E [CNT]. CAP = 0; E [CNT]. flow = 0; E [CNT]. NXT = G [v]; G [v] = C NT;} bool check (int x, int y) {for (INT I = 0; I <p; I ++) if (s [y] [I]! = 2) {If (s [y] [I]! = D [x] [I]) return false;} return true;} void Init () {MEM (G, 0); CNT = 1; scanf ("% d", & P, & N); ST = 0, ED = n + 1; int OK; For (INT I = 1; I <= N; I ++) {scanf ("% d", q + I); OK = 0; For (Int J = 0; j <P; j ++) {scanf ("% d", s [I] + J); If (s [I] [J] = 1) OK ++ ;} if (! OK) add (St, I, Q [I]); OK = 0; For (Int J = 0; j <p; j ++) {scanf ("% d", d [I] + J); If (d [I] [J] = 1) OK ++ ;} if (OK = P) add (I, Ed, Q [I]) ;}for (INT I = 1; I <= N; I ++) {for (Int J = I + 1; j <= N; j ++) {If (check (I, j) add (I, j, min (Q [I], Q [J]); If (check (J, I) add (J, I, min (Q [I], Q [J]) ;}}n = N + 3;} int Dist [maxn], numbs [maxn], Q [maxn]; void rev_bfs () {int font = 0, rear = 1; for (INT I = 0; I <= N; I ++) {// n indicates the total number of DIST [I] = maxn; numbs [I] = 0 ;} Q [font] = Ed; Dist [ed] = 0; numbs [0] = 1; while (font! = Rear) {int u = Q [font ++]; for (INT I = G [u]; I; I = E [I]. NXT) {If (E [I ^ 1]. CAP = 0 | Dist [E [I]. v] <maxn) continue; Dist [E [I]. v] = DIST [u] + 1; ++ numbs [Dist [E [I]. v]; Q [rear ++] = E [I]. V ;}}int maxflow () {rev_bfs (); int U, totalflow = 0; int curg [maxn], revpath [maxn]; for (INT I = 0; I <= N; ++ I) curg [I] = G [I]; u = sT; while (Dist [st] <n) {If (u = ed) {// find an Augmenting Path int augf Low = inf; For (INT I = sT; I! = Ed; I = E [curg [I]. v) augflow = min (augflow, E [curg [I]. CAP); For (INT I = sT; I! = Ed; I = E [curg [I]. v) {e [curg [I]. cap-= augflow; E [curg [I] ^ 1]. cap + = augflow; E [curg [I]. flow + = augflow; E [curg [I] ^ 1]. flow-= augflow;} totalflow + = augflow; u = sT;} int I; for (I = curg [u]; I; I = E [I]. NXT) if (E [I]. cap> 0 & Dist [u] = DIST [E [I]. v] + 1) break; if (I) {// find an admissible arc, then advance curg [u] = I; revpath [E [I]. v] = I ^ 1; u = E [I]. v;} else {// no admissible arc, Then relabel This vertex if (0 = (-- numbs [Dist [u]) break; // gap cut, important! Curg [u] = G [u]; int mindist = N; For (Int J = G [u]; j = E [J]. NXT) if (E [J]. cap> 0) mindist = min (mindist, DIST [E [J]. v]); Dist [u] = mindist + 1; ++ numbs [Dist [u]; If (u! = ST) u = E [revpath [u]. v; // backtrack} return totalflow;} int out [maxm] [3], TOT = 0; void get_out () {for (INT u = 1; U <ED; U ++) {for (INT I = G [u]; I; I = E [I]. NXT) {If (E [I]. v! = ED & E [I]. flow> 0) {out [tot] [0] = u; out [tot] [1] = E [I]. v; out [tot ++] [2] = E [I]. flow ;}}} int main () {Init (); printf ("% d", maxflow (); get_out (); printf ("% d \ n ", TOT); For (INT I = 0; I <tot; I ++) {printf ("% d \ n", out [I] [0], out [I] [1], out [I] [2]);} return 0 ;}
Poj 3436 ACM computer factory (maximum stream + output path)