思考:Dinicは、スーパーソース(S)およびスーパーシンク(T)を構築するために、二部グラフマッチングを実現N + M + 1、N + M + 2に設定しました。
S及びN、次に正側の数と反対側を構築するためには、右側が正、抗エッジ重み値が0であり; mは、正の側と反対側を構築するためのTの数、1の重みの正側です。
N、Mの間で構築された図において同じ番号
そして、最大のフローを実行するために行ってきました。
注意:たCur SとTも更新する必要がありDinicたCur更新機能の各値を。
コード:
1の#include <cstdioを> 2の#include <CStringの> 3の#include <iostreamの> 4 の#define分(A、B)((A)<(B)(A):( B?)) 5 使用 名前空間STD。 6 CONST INT MAXN = 1050、MAXM = MAXN、MAXE = MAXM * MAXN。 7 整数 N、M、U、V、E、num_edge = - 1、edge_head [MAXN + MAXM]、Q [MAXN + MAXM]、F1、F2、発[MAXN + MAXM]。 8 INT S、T、たCur [MAXN + MAXM]。 9 構造体のエッジ{ INT に、NX、DIS;}エッジ[MAXE]。 10インライン無効 Add_edge(INT から、INTに、INT DIS){ 11 エッジ[++ num_edge] .nx = edge_head [ から]。 12 エッジ【num_edge] = .TO に、 13 エッジ【num_edge] .DISの=のDIS。 14 [edge_head から =] num_edge。 15 リターン; 16 } 17インラインBOOL BFS(){ 18 のmemset(DEP、0、はsizeof (DEP))。 19 = F2、F1 = 1 ; 20 発[S] = 1 。 21 Q [F 2 ++] =のS。 22 一方(F1 < F2){ 23 、INT X = Q [F1 ++ ]。 24 のために(INT!I = edge_head [X]; I = - 1 ; I = エッジ[I] .nx){ 25 のint Y = エッジ[I] .TO。 26 であれば(エッジ[I] .DIS &&発[Y] == 0 ){ 27 発[Y] =発[X] + 1 。 28 Q [F 2 ++] = Y。 29 } 30 } 31 } 32 であれば(DEP [T])リターン 1 ; 33 リターン 0 ; 34 } 35インラインINTのDFS(int型のx、int型FW){ 36 であれば(X == T)戻りFW。 37 のために(INT!; I = - &I = curが[X] 1 ; I = エッジ[I] .nx){ 38 のint Y = エッジ[I] .TO。 39 であれば(DEP [Y] ==発[X] + 1つの && エッジ[I] .DIS){ 40 のint p = のDFS(Y、分(エッジ[I] .DIS、FW))。 41 もし(P> 0 ){ 42 エッジ[I] .dis- = P。 43 エッジ[I ^ 1 ] .DIS + = P。 44 リターンのp; 45 } 46 } 47 } 48 リターン 0 。 49 } 50インラインINT Dinic(){ 51 INT ANS = 0 。 52 一方(BFS()){ 53 のint TOI = N + M + 2 。 54 のために(int型 I = 1 CURが[I] =; I <= TOI I ++)はedge_head [I]。 55 一方(int型 K =のDFS(S、1 << 30))ANS + = K。 56 } 57の リターンANS。 58 } 59 INT メイン(){ 60 のmemset(edge_head、 - 1、はsizeof (edge_head))。 61 のscanf(" %D%D%D "、&N、&M、&E); 62個の S = N + M + 1、T = N + M + 2 。 63 のために(int型 i = 1 ; iが= Nを<Iは++ ){ 64 Add_edge(S、I、1 )。 65 Add_edge(I、S、0 ); 66 } 67 INT TOI = N + M。 68 のためには、(int型、I = N + 1 ; I <= TOI; iは++ ){ 69 Add_edge(I、T、1 ); 70 Add_edge(T、I、0 ); 71 } 72 のための(int型 i = 1 ; iは= Eを<I ++は{) 73 のscanf(" %d個の%のD "、&U、およびV)。 74 もし(V> M || U> N)続けます。 75 V + = N。 76 Add_edge(U、V、1 )。 77 Add_edge(V、U、0 ); 78 } 79 のprintf(" %d個の\ n " 、Dinic())。 80 リターン 0 ; 81 }
で:AlenaNuna