ACM-ICPC 2018ネットワーク瀋陽分割予備F.幻想グラフ(アクティブシンクネットワークフロー境界板)

ボードの質問

点は、n、m個の点は反対側に、縁部をk個ながら、すべての点は度で[L、R]であるように、削除するエッジによって求めることができ、あなたの二部グラフを得ました

#include <ビット/ STDC ++。H>
 に#define FIN freopenは( "INPUT.TXT"、 "R"、STDIN)
 の#define LL長い長
 の#define MOD十億七
 の#define LSONのL、M、RT << 1
 の#define rson mを+ 1、R、RT << 1つの| 1つ
 の#define INF 0x3f3f3f3f
 の#define INF 0x3f3f3f3f3f3f3f3f
 のconst  int型 MAXN = 100005 使用して 名前空間はstdを、
INT CNT、S、T、N、M、K。
int型のヘッド[MAXN]、次に[MAXN * 20まで]、[MAXN * 20 ]。
INTの流れ[MAXN * 20 ]、DEP [MAXN]、cur変換[MAXN]、MP [ 405 ] [405 ]。
INT DIR [ 8 ] [ 2 ] = { 121、 - 2、 - 12、 - 1、 - 2、 - 2、 - 1、 - 21212、 - 1 } ; 
インラインボイド追加(INT U、INT V、INT W){ 
    次に[CNT] = 頭部[U]。
    ヘッド[U] = CNT。
    [CNT]へ = V。
    流れ【CNT ++] = W。

    次の[CNT] = 頭部[V]。
    ヘッド[V] = CNT。
    [CNT]へ = U。
    流れ【CNT ++] = 0 ; 
} 
INT DFS(INT U、int型のコスト){
     場合(Uは== T)戻りコスト。
    INT - ;!I =&I = CUR [U] 1 ; I = {次に[I])
         であれば(== DEP [U] + [I]乃至] DEP 1 &&流量[i]が> 0 ){
            int型 DIS =DFS([i]は、分([i]が流れるように、コスト))。
            場合(DISは> 0 ){ 
                [i]が流れる =の- ; DISを 
                流動[I ^ 1 ] + = DIS。
                返すDISを。
            } 
        } 
    } 
    戻り 0 
} 
int型BFSを(){ 
    キュー < INT > Q。
    q.push(S); 
    memset(DEP、0はsizeof (DEP))。
    DEP [S] = 1 しばらく(!q.empty()){
        INT U = q.front()。
        q.pop(); 
        以下のためにint型 - ;!I = I =ヘッド[U] 1 ; I = {次に[i])と
             する場合([I]>流れる0 == [[I]に] && DEPを0 {)
                DEP [I]に] = DEP [U] + 1 
                ([I]に)q.push。
            } 
        } 
    } 
    もし(DEP [T]> 0リターン 1 リターン 0 ; 
} 
INT dicnic(){
     int型 ANS = 0 同時に(BFS()){
         int型のコスト。
        以下のためにint型 i = 0 ; I <= T + 2、iが++ ){ 
            CUR [I] = 頭部[i]は、
        } 
        一方、(コスト=のDFS(S、INF))
            ANS + = コスト。
    } 
    戻りANS。
} 
int型 P [ 200005 ]。
ボイドのinit(){ 
    memsetの(頭、 - 1はsizeof (ヘッド))。
    memsetの(p、0はsizeof (P))。
    CNT = 0; 
} 
のInt のmain(){
     int型 CAS = 0 ;
     ながら(〜scanfの(" %D%D%D "、およびN-、&M&K)){ 
        INIT(); 
        int型のL、R&LT;
         int型 SS = 0 ; / / ソース
        INT TT = N + M + 1 ; // シンク 
        S = N + M + 2 ; // スーパーソース 
        T = N + M + 3 ; // スーパーシンク
        int型 SUM = 0 ; 
        scanfの(" %D% D "、L&、&R);
        以下のためにint型 i = 1 ; iは= Kを<; iは++ ){
             int型Uを、V。
            scanf関数(" %d個の%d個"、&​​U&V); 
            追加(U、V + nは、1 )。
        } 
        のためにint型 I = 1は iが++; iがn = < {)
            を追加(SS、I、R - L)。
            P [I] + = L。
        } 
        のためにint型 iは= 1 ; iが<= M iは++ ){ 
            I(追加 + nは、TT、R-  L);
            P [I+] -N - = L。
        } 
        のためにint型 i = 1 ; iが<= N + Mは、iは++ ){
             場合(P [i]は< 0)を追加(I、T、 - P [I])。
            他の追加(複数可、I、P [i])と、合計+ = P [i]は、
           // のprintf( "%dの--->%D \ n"は、I、P [I])。
        } 
        (TT、SS、INF)を加えます。
        printf(" ケースは%d:"、++ CAS)。
        もし(合計== dicnic())
            プット(" はい" )。
        他のプット(ノー)。 
    } 
}
コードの表示

 

おすすめ

転載: www.cnblogs.com/MengX/p/11369209.html