HDU-4289コントロール(最小カット、スプリットポイント)

トピックリンク:HDU-4289コントロール

問題の意味

テロリストは、市内交通$ Sの$の$ Dが$に市から武器を計画し、そして今、私たちは$ S $と$ D $は、彼らのニーズ市内各ブロックのコストを知っている、市はネットワークパス(無向辺)に存在することがわかっていることを知っています我々はテロリストの閉塞さ都市は最小のコストが必要とされるすべてのテロリストを逮捕しようと、逮捕され達し、都市の任意の封鎖を行うことができます。


考え

これは明らかに最小カットの問題であるが、価格の点は右の代わりに右側であるので、それも側を指すように、都市やポイントにポイントを各ノードのオーバーホールが必要で、ノード対応都市の右側右のポイントは、この時点では価格適切な価格の右側に変換されます。双方向パス$(U、V)$、$ U $ $ Uに$ $ 'エッジ点、アウト点の$のV $のV $に接続$ $ $ $ V $ V' への異なる都市ポイント間点$ U $ U $偶数側は、右側は、カッティングエッジとして表現することができない、無限です。S $ $源が点の点は、$ D $シンク点で、最小ランを切断することができます。


コードの実装

書式#include <iostreamの> 
の#include <cstdioを> 
する#include <CStringの> 
の#include <キュー>
 使用してのstd ::キューを。
CONST  INT INF = 0x3f3f3f3f、N = 500、M = 100000 int型のヘッド[N]、D [N]。
int型S、T、TOT、maxflow。
構造体のエッジ
{ 
    int型キャップに、NEX。
}エッジ[M]。
キュー < 整数 > Q;
ボイド追加(int型のx、int型の Y、int型Z){ 
    エッジ[++ TOT] .TO = Y、エッジ[TOT]の.cap = Z、エッジ[TOT] .nex =頭部[X]、ヘッド[X] = TOT。
    エッジ[ ++ TOT] .TO = xで、エッジ[TOT]の.cap = 0、エッジ[TOT] .nex =頭部[Y]、ヘッド[Y] = TOT。
} 
BOOL BFS(){ 
    memsetの(D、0はsizeof (d)参照)。
    一方、(q.size())q.pop(); 
    q.push(S); D [S] = 1 一方、(q.size()){
         int型 X = )(q.front。q.pop();
        以下のためにint型 ; I I = I =ヘッド[X] {エッジ[I] .nex)
             のint V = エッジ[I] .TO。
            もし(!エッジ[I]の.cap && D [V]){ 
                q.push(V)。
                D [V]、D [X] + = 1 もし(V == t)が復帰 
            } 
        } 
    } 
    を返す 
} 
int型 dinic(int型のx、int型フロー){
     場合(X == T)リターンフロー。
    int型の残り= 流れ、K。
    int型 ; iが残り&& I = I =ヘッド[X]を{エッジ[I] .nex)
         int型、V =エッジ[I] .TO。
        もし(エッジ[I]の.cap && D [V] == D [X] + 1 ){ 
            K = dinic(V、STD ::分(残り、エッジ[I]の.cap))。
            もし(!k)のD [v] = 0 ; 
            エッジ[I]の.cap - = K。
            エッジ[I ^ 1 ]の.cap + = K。
            残り - = K; 
        } 
    } 
    戻り流- 安静。
} 
ボイドのinit(){ 
    TOT = 1、maxflow = 0 
    memsetの(頭、0sizeof (ヘッド))。
} 

int型のmain(){
     int型、N M。
    一方、(〜のscanf(" %d個の%のD "、&​​N、&M)){ 
        INIT()。
        scanf関数(" %dの%のD "、&​​S&T)。
        T + = N。
        以下のためにint型 I = 1、ヴァルと、iが<= N; iが++ ){ 
            scanf関数(" %のD "、およびヴァル)。
            (iは、iが追加 + 、Nヴァル)。
        } 
        のためにint型のI =0、U、V; 私は<M。私は++ ){ 
            scanf関数(" %d個の%dを"、&​​U、およびV)。
            追加(U + N、V、INF)。
            (V追加 + N、U、INF)を、
        } 
        一方(BFS())maxflow + = dinic(S、INF)。
        printf(" %d個の\ n " 、maxflow)。
    } 
    戻り 0 
}
コードの表示

 

おすすめ

転載: www.cnblogs.com/kangkang-/p/11332814.html