hdu 2444(染色法判断二分图+匈牙利算法)

题意:首先判断是否是二分图,如果不是的话输出No,如果是的话输出最大匹配

判断二分图:运用染色法,相邻的两个点间染不同的颜色,如果遇到相邻的点是同一颜色的,则不是二分图

具体实现:通过广搜遍历所有的点,判断是否有相邻的点是同一颜色(一定要遍历所有的点),找最大匹配的时候就用匈牙利算法,最后找到的count要除以2,因为找最大匹配的时候每个点都找了,所以求出的count值是最大匹配的二倍

网上好多代码都过不了这组数据,因为没有遍历所有的点,表示这一题数据有点水

4 3

2 3

2 4

3 4

#include
#include
#include
#include
using namespace std;
const int N=205;
int flag[N];
int map[N][N];
int match[N];
bool link[N];
int n,m;
int bfs()
{
    int j;
	memset(flag,-1,sizeof(flag));
	for(j=1;j<=n;j++)
	{
	if(flag[j]!=-1) continue;
	queue q;
	flag[j]=1;
    q.push(j);
	while(!q.empty())
	{
		int k=q.front();
		q.pop();
		for(int i=1;i<=n;i++)
		{
			if(map[k][i]&&flag[i]==flag[k])
			{
		    	return 0;
			}
			if(map[k][i]&&flag[i]==-1)
			{
				q.push(i);
				flag[i]=1-flag[k];
			}
		}
	}
	}
	return 1;
}
bool find(int x)
{
	int i,k;
	for(i=1;i<=n;i++)
	{
		if(map[x][i]==1)
		{
		  k=i;
		   if(!link[k])
		   {
			link[k]=true;
			if(!match[k]||find(match[k]))
			{
				match[k]=x;
				 return true;
			}
		   }
		}
	}
	return false;
}
int main()
{
	int a,b;
	while(~scanf("%d%d",&n,&m))
	{
	 memset(map,0,sizeof(map));
     while(m--)
	 {
		 scanf("%d%d",&a,&b);
		 map[a][b]=1;
		 map[b][a]=1;
	 }
     if(!bfs())
	 {
		 printf("No\n");continue;
	 }
	 int count=0;
     memset(match,0,sizeof(match));
	 for(int i=1;i<=n;i++)
	 {
		memset(link,false,sizeof(link));
		 if(find(i))
		 {
			 count++;
		 }
	 }
	 printf("%d\n",count/2);
	}
	return 0;
}


 


 

你可能感兴趣的:(图论,搜索)