【二分图最大匹配-匈牙利算法及其优化算法模板】

来源:互联网 发布:桂正和is知乎 编辑:程序博客网 时间:2024/05/29 06:37

一、匈牙利算法

1.N是点数,下标1-n2.用g.push_back建图后,直接调用max_macth()得到最大二分匹配3.最终,liky表示与“y轴”上i匹配的值。const int N=1000;vector<int> g[N];int lik[N],n,m;bool visy[N];bool dfs(int x){    for(int i=0;i<g[x].size();i++)    {        int y=g[x][i];        if(visy[y])continue;        visy[y]=true;        if(lik[y]==-1||dfs(lik[y]))        {            lik[y]=x;            return true;        }    }    return false;}int max_match(){    int ret=0;    memset(lik,-1,sizeof(lik));    for(int i=1;i<=n;i++)    {        memset(visy,false,sizeof(visy));        if(dfs(i))ret++;    }    return ret;}

二.HK算法(优化的匈牙利)

1.N表示点数,下标1-n,一般N超过300才用HK算法2.直接调用max_macth()得到答案3.const int N=1000;vector<int> g[N];int mx[N],my[N],dx[N],dy[N],dis,n,m;bool vis[N];int bfs(){    dis=INF;    memset(dx,-1,sizeof(dx));    memset(dy,-1,sizeof(dy));    queue<int> que;    for(int i=1;i<=n;i++)        if(mx[i]==-1)    {        que.push(i);        dx[i]=0;    }    while(!que.empty())    {        int x=que.front();que.pop();        if(dx[x]>dis)break;        for(int i=0;i<g[x].size();i++)        {    int y=g[x][i];             if(dy[y]!=-1)continue;            dy[y]=dx[x]+1;            if(my[y]==-1)dis=dy[y];            else            {                dx[my[y]]=dy[y]+1;                que.push(my[y]);            }        }    }    return dis!=INF;}int dfs(int x){    for(int i=0;i<g[x].size();i++)    {int y=g[x][i];       if(vis[y]||dy[y]!=dx[x]+1)continue;        vis[y]=true;        if(my[y]!=-1&&dy[y]==dis)continue;        if(my[y]==-1||dfs(my[y]))        {            my[y]=x;            mx[x]=y;            return 1;        }    }    return 0;}int max_macth(){    int ret=0;    memset(my,-1,sizeof(my));    memset(mx,-1,sizeof(mx));    while(bfs())    {        memset(vis,false,sizeof(vis));        for(int i=1;i<=n;i++)            if(mx[i]==-1&&dfs(i))ret++;    }    return ret;}



阅读全文
0 0
原创粉丝点击