1つの#include <ビット/ STDC ++ H> 2 使用して 名前空間STDを、 3 CONST INT MAXN = 305、INF = 0x3f3f3f3f 。 4 構造体のエッジ{ 5 INT から、キャップに、フロー、コスト。 6 }。 7 8 構造体MCMF { 9 int型N、M、S、T。 10 ベクター<エッジ> エッジ。 11 ベクター< INT > G [MAXN]。 12 INT [MAXN] INQ。 13 int型D [MAXN]。 14 int型P [MAXN]。 15 INT [MAXN]。 16 17 ボイドのinit(int型N){ 18 本 - > N = N。 19 のためには、(int型、I = 1 ; ++; iが<= N I)G [i]が.clear(); 20 edges.clear()。 21 } 22 23 空隙 AddEdge(INT から、INTに、int型のキャップ、int型の{コスト) 24 edges.push_back((エッジ){ から、に、キャップ、0、コスト})。 25 edges.push_back((エッジ){に、から、0、0、 - コスト})。 26 、M = edges.size()。 27 G【から】.push_back(M- 2 )。 28 .push_back【に】G(M- 1 )。 29 } 30 BOOL BellmanFord(INT S、INT T、INT&流れ、INT&コスト){ 31 のためには、(int型 i = 1 ; iが<= N; ++ I)D [i]は=infファイル。 32 のmemset(INQ、0、はsizeof (INQ))。 33 D [S] = 0 ; INQ [S] = 1。P [S] = 0 ; [S] = INF。 34 35 キュー< 整数 > QUE。 36 que.push(S); 37 ながら(!que.empty()){ 38 INT U = que.front()。que.pop(); 39 INQ [U] = 0 。 40 のためには、(int型、I = 0 ; iが[U] .size()Gを<; ++I){ 41 エッジ&E = 縁[G [U] [I]]。 42 であれば(e.cap> e.flow && D [e.to]> D [U] + e.cost){ 43 D [e.to] = D [U] + e.cost。 44 P [e.to] = G [U] [I]。 45 [e.to] =分([U]、e.cap- e.flow)。 46 もし {que.push(e.to)(INQ [e.to]!)。INQ [e.to] = 1 。} 47 } 48 } 49 } 50 場合(D [T] == INF)を返し 偽。 51 フロー+ = [T]。 52 費用+ = D [T] * [T]。 53 INT U = T。 54 ながら(!U = S){ 55の 。エッジ[P [U]フローは+ = [T]。 56の エッジ[P [U] ^ 1 ] .flowは- = [t]を。 57 U =エッジ[P [U]。から; 58 } 59 リターン 真。 60 } 61 INT mincost(INT S、INT T){ 62 int型フロー=0、コスト= 0 。 63 一方(BellmanFord(S、T、流量、コスト))。 64 リターン・コスト; 65 } 66 } MCMF。 67 int型のC [MAXN] [MAXN]。 68 INT メイン(){ 69 INT N。scanf関数(" %のD "、&N) 70 INT = S 2 * N + 1、T = 2 * N + 2 。 71 72 のために(int型 i = 1 ; iが<= N ++ {I) 73 用(INTの J = 1 ; J <= N; ++ j)は{ 74 のscanf(" %dの"、&C [I] [J])。 75 } 76 } 77 78 /// 最小总效益 79 mcmf.init(2 * N + 2 )。 80 のために(int型 i = 1 ; iが<= N ++ {I) 81 のための(INT J = 1 ; J <= N; ++ j)は{ 82 mcmf.AddEdge(I、J + nは、1、C [I] [J])。 83 } 84 } 85 のための(int型 i = 1 ; iは= N <; ++ I){ 86 mcmf.AddEdge(S、I、1、0 ); 87 mcmf.AddEdgeは、(iは、N T + 1、0 ); 88 } 89 INT ANS = mcmf.mincost(S、T)。 90 のprintf(" %d個の\ n " 、ANS)。 91 92 /// 最大总效益 93 mcmf.init(2 * N + 2 )。 94 のために(int型 i = 1 ; iが<= N; ++ I){ 95 のために(INT J = 1 ; J <= N; ++ j)は{ 96 mcmf.AddEdge(I、J + N、1、 - C [I] [J])。 97 } 98 } 99 のための(int型 i = 1 ; iが<= N; ++ I){ 100 mcmf.AddEdge(S、I、1、0 ); 101 mcmf.AddEdge(iはN、T + 1、0 ); 102 } 103 ANS = mcmf.mincost(S、T)。 104 のprintf(" %d個の\ n "、 - ANS)。 105 戻り 0 ; 106 }