HDU - 2444学生の宿泊施設(決意二部グラフ、最大2部グラフマッチング)

質問の意味:人々の範囲の数N与えられ、その後、数AB間の理解の関係を与えます。このような関係が指定されたm個のセットは、その後2を分離させ
、各グループ内のそれぞれの人が(間接的な関係を認識していない)お互いを知らないように、そのパケットならば、それが認識され、その部屋に2人、客室には必要性の中で最も求めて
最初のすべてのセットを試してみて、確認したい(互いに素-設定されたグループが開いて二倍の配列である)ので、パケットにばらばら設定された質問の前に行わ:アイデアを
しかし、自己分析を考えるとセットポイントをチェック実際にそこに間接的な関係があるだけでなく、部屋を割り当てる方法を決定できない場合
、次に検討:二部グラフマッチング
部グラフマッチング問題があれば、二つの点の間にエッジが存在するように、マップが与えられ、2つのポイントができません両側でなければならない点の集合に属しています。
(1)二部グラフを決定する:この質問は、それは二部グラフであるか否かを判定する
方法:染色:我々は、特定の地点から開始し、その後染色1,2が接続されDianranへの接続を染色することができ場合
ポイントが接続され、それは1、これは確かに二部グラフはない染色された
二部グラフの最大マッチング:二十から二、すなわち、我々はできると共に理解我々はできるだけ与えられた図の(2)毎回
2人の間に一定の関係、およびマップを思い付きます。残りの試合は「パスを増大させる」見つけていきます
パスを増強(:、Bのコレクションがあり、ルートA、点Bは、この点のリードを作っポイント、そしてA、B、ポイントにつながる、増補しました......交互)

完全なコード:

書式#include <iostreamの> 
の#include <ベクトル> 
の#include <CStringの>
 使用して 名前空間はstdを、
const  int型 MAXN = 10010 ;
INTの N、M。// 顶点数边数 
ベクター< INT > G [MAXN]。
int型[MAXN] VIS [MAXN]、試合;
INTの色[MAXN]。
// 0没染色1 -1不同色
BOOL DFS(INT U、INT C){ 
    色[U]は = Cと、
    以下のためにint型 iは= 0 ; iは、Gを<U] .size(); iは++ ){
        int型 V = G [U] [I];
         // 同じ色ではない
        IF(色[V] == C)     復帰 はfalse ;
         // V染色なし、再帰的に染色することは、これが確立されたか否かを判断する
        IF(色[V] = = 0 && DFS(V、-C))!     戻り falseに; 
    } 
    戻り trueに; 
} 

BOOL (解決){
     ためINT I = 1 ; I <= N; I ++は){
         IF(色[I] == 0 IF(!DFS(I、1 )){
                 返す falseに
            } 
    } 
    戻り値 をtrueに; 
} 
// ハンガリーアルゴリズム:DのFSの増強パスが見つかり
 BOOL検索(INT U)
{ 
    ためint型 I = 0 ; I ++は、IはG [U] .size()< 
    { 
        int型 X = Iと、
         IF(!VIS [X] && G [U] [X])
        { 
            VIS [X] = 1 ;
             IF(一致[X] ||!検索(一致[X]))
            { 
                一致[X] = U;
                 リターン 
            } 
        } 
    } 
    を返す 
} 

int型のmain(){
     int型のT。
    cinを >> トン。
    一方、(t-- ){ 
        CIN >> N >> M。
        memsetの(色、0はsizeof (色))。
        以下のためにint型 i = 0 ; iは<MAXN; iは++ )G [i]が.clear();
        以下のためにint型 i = 0 ; iがm <I ++の
        { 
            int型のS、Tと、
            CIN >> S >>T; 
            G [S] .push_back(T); 
            G [T] .push_back(S);   // 図文する必要がない場合
        } 
        
        IF (解決()){ 
            memsetの(一致、0はsizeof (一致) );
             のためのINT I = 1 ; I <= N; I ++ ){ 
                memsetの(VIS、0はsizeof (VIS));
                 IF(検索(I))ANS ++ ; 
            } 
            COUT << ANS / 2 << ENDL; 
        } 
        他の     裁判所未満<< ノー<< てendl; 
    } 
    
    戻り 0 

}

BFS染色:

BOOL BFS(int型S){ 
     カラー[S] = 1 ; 
     キュー < INT > Q; 
     q.push(S); 
     ながら(!q.empty()){
          int型 U = q.front(); 
         q.pop( ); 
         のためのint型 V = 1 V <= N; V ++ ){
              // 隣接しない染色
             IF(G [U] [V] &&色[V] == 0 ){ 
                 q.push(V)。
                 色[V] = -color [U]; // 異なる色染め
             }
              IF(G [U] [V] &&色[U] == 色[V]){
                  リターン falseに; 
             } 
         } 
     } 
     // すべてのノードと隣接ノードが染色される異なる色を
     返す trueに; 
 }

 

おすすめ

転載: www.cnblogs.com/Tianwell/p/11329268.html