二分圖的最大匹配(匈牙利算法)

看書看了好久,看不懂。
上網找代碼研究,還是不懂。
突然瞄到書上的插圖,頓悟,哈哈^_^
這裏的代碼修改了一些,貼上來。。


// 二分圖的最大匹配(匈牙利算法)
#include <cstdio>
#include 
<memory.h>
using namespace std;

const int XV = 100;
const int YV = 300;
int xv, yv;        // X , Y 點集的大小
int adj [XV] [YV];    // adj [i] [j] != 0 表示 xi 與 yj 鄰接
bool sy [YV];        // 每輪中對於被搜過的點 yi , sy [i] = 1
int xm [XV];        // xm [i] 保存 xi 匹配的 Y 點
int ym [YV];        // ym [i] 保存 yi 匹配的 X 點


int path (int u)
{
    
//對於 X 中的點 u ,返回能否找到增廣路(也即能否增大匹配數,遞歸,時間複雜度 O (xv * yv))
    for (int v = 0; v < yv; v ++)
        {
        
if (adj [u] [v] && !sy [v])
            { 
            sy [v] 
= true;
            
if (ym [v] == -1 || path (ym [v]) == 1)
                {
                xm [u] 
= v;
                ym [v] 
= u;
                
return 1;
                } 
            }
        }
    
return 0;   
}

int maxmatch ()
{
    
int cnt = 0;            // 匹配數
    memset (xm, -1sizeof (xm));    // xm [i] == -1 表示 xi 尚未匹配
    memset (ym, -1sizeof (ym));
    
for (int u = 0; u < xv; u ++)
        {
        
if (xm [u] == -1)
            {
            memset (sy, 
0sizeof (sy));
            cnt 
+= path (u);
            }
        }
    
return cnt;
}

int main()
{
    scanf (
"%d%d"&xv, &yv);    // 輸入 X , Y 點集的大小

    
// 輸入鄰接矩陣,兩種方式

    
int edge;
    scanf (
"%d"&edge);        // 輸入邊數
    memset (adj, 0sizeof (adj));    
    
for (int i = 0; i < edge; i ++)
        {
        
int u, v;
        scanf (
"%d%d"&u, &v);    // 輸入關聯的兩點
        adj [u] [v] = 1;
        }
    
/*
    6 6 10
    0 0
    0 2
    1 3
    1 5
    2 1
    2 3
    3 4
    4 4
    4 5
    5 5
    6 6
    
*/
/*************************************************
    for (int i = 0; i < xv; i ++)
        {
        for (int j = 0; j < yv; j ++)
            {
            scanf ("%d", &adj [i] [j]);
            }
        }
*/
/*    
    1 0 1 0 0 0
    0 0 0 1 0 1
    0 1 0 0 0 1
    0 0 0 0 1 0
    0 0 0 0 1 1
    0 0 0 0 0 1
*************************************************
*/

    
int cnt = maxmatch ();        // 匹配

    
// 打印
    printf ("The maxmatch count is %d ", cnt);
    
for (int i = 0; i < xv; i ++)
        {
        printf (
"%d ", xm [i]);
        }
    
return 0;
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章