hrbeu 哈工程The Accomodation of Students

经典题目,HDU上也有,给定一个无向图,先判断是否为二分图,不是输出No,是的话,输出最大匹配,算是一个模板题

1.一个图不存在奇环则是二分图

2.二分图最大匹配用匈牙利算法

 

#include <cstdio>

#include <cstring>

#define N 210

int g[N][N];  //无向图领接表

int mat[N],cov[N],vis[N],c[N];

int n,m;



void input()

{

    memset(g,0,sizeof(g));

    for(int i=1; i<=m; i++)

    {

        int u,v;

        scanf("%d%d",&u,&v);

        int t;

        t=++g[u][0];

        g[u][t]=v;

        t=++g[v][0];

        g[v][t]=u;

    }

    return ;

}



int dfs(int u ,int p) //u是当前顶点,p是它的前驱,c表示奇偶

{

    vis[u]=1;

    for(int i=1; i<=g[u][0]; i++)

    {

        int v=g[u][i];

        if(v==p) continue;   //如果是前驱跳过,不能走回头

        if(vis[v]==0)       //还没访问过的点,直接访问

        {

            c[v]=!c[u];

            if(dfs(v,u)) 

                return 1;

        }

        else if(vis[v]==1)  //已经访问过,那么就是环,那么就判断是不是奇环

        {

            if( c[u]==c[v] )  //加上成环的边后是奇数,那么就是奇环

                return 1;

        }

    }

    return 0;

}



int find(int u)

{

    for(int i=1; i<=g[u][0]; i++)

    {

        int v=g[u][i];

        if(!cov[v])

        {

            cov[v]=1;

            if(!mat[v] || find(mat[v]))

            {

                mat[v]=u;

                return 1;

            }

        }

    }



    return 0;

}

void max_match()

{

    int ans=0;

    memset(mat,0,sizeof(mat));

    for(int i=1; i<=n; i++)

    {

        memset(cov,0,sizeof(cov));

        ans+=find(i);

    }

/*

    printf("mat数组\n");

    for(int i=1; i<=n; i++)

        printf("%d ",mat[i]);

    printf("\n");

    printf("ans=%d\n",ans);

*/



    printf("%d\n",ans/2);

}

int main()

{

    while(scanf("%d%d",&n,&m)!=EOF)

    {

        input();

        memset(vis,0,sizeof(vis));

        memset(c,0,sizeof(c));

        int flag=1;

        for(int i=1; i<=n; i++)

            if(!vis[i])

            {

                if(dfs(i,0))

                {flag=0; break;}

            }

        if(!flag)

            printf("No\n");

        else

            max_match();

    }

    return 0;

}

你可能感兴趣的:(com)