zoukankan      html  css  js  c++  java
  • AcWing 860. 染色法判定二分图

    AcWing 860. 染色法判定二分图

    860. 染色法判定二分图
    给定一个 n 个点 m 条边的无向图,图中可能存在重边和自环。
    请你判断这个图是否是二分图。

    • 二分图里面可能存在多个联通块
    • 二分图:把点分成两个集合,且线段上的两点比分属于两个不同的集合(阵营),当出现第三个集合(阵营时),该图不是二分图。
    • 比如某个世界存在两个忍屯,忍者小a属于忍屯A,忍者小b属于忍屯B,小a和小b之间有一条皇帝的线来牵着,表示他们是不同屯的。有一天,发现有一个忍者小c和忍者小a、小b都各自有一条线牵着,经过推断,小c是属于第三个屯,可得这个世界中的地图也并不是只有两个屯的图。
    #include<bits/stdc++.h>
    using namespace std;
    const int N = 1e5+10;
    int color[N];
    
    int h[N],e[N*2],ne[N*2],idx=0;
    void add(int a,int b)
    {
    	e[idx]=b,ne[idx]=h[a],h[a]=idx++;
    }
    int n,m;
    
    
    bool BFS_biparts(int u)
    {
    	queue<int > q;
    	q.push(u);
    	color[u]=1;
    	while(q.size())
    	{
    		int t = q.front();
    		q.pop();
    		for(int i = h[t];~i;i=ne[i])
    		{
    			int j=e[i];
    		    if(!color[j])
    		    {
    		    	color[j]=3-color[t];//用1和2来表示不同的颜色,也可以用0和1,其中可以用~来实现转换 
    		    	q.push(j);
    			}
    			else
    				if(color[j]+color[t]!=3)
    				   return false;
    		}    
    	}
    	return true;
    }
    int main()
    {
    	cin>>n>>m;
    	memset(h,-1,sizeof(h));
    	memset(color,0,sizeof(color));
    	for(int i=0;i<m;i++)
    	{
    		int a,b;
    		cin>>a>>b;
    		add(a,b);add(b,a);
    	}
    	int flag=1;
    	for(int i=1;i<n;i++)//搜遍每一个联通块 
    	{
    		if(color[i]==0)
    		{
    			if(!BFS_biparts(i))
    			{
    				flag=0;
    				break;
    			}
    		}
    	}
    	
    	if(flag)cout<<"Yes";
    	else cout<<"No";
    	return 0;
    }
    
    
  • 相关阅读:
    java实现前n项和,要求不使用循环、乘除法、判断标识
    java 线程池 带返回值
    java 多线程 数据通信
    jedis使用分布式锁
    记一次自定义管理工厂使用spring自动装载bean
    面试题玩数组
    记一次随便排序算法
    九九乘法表打印记一次al面试
    多线程操作共享变量顺序输出abc 记一次al面试题
    博客迁移
  • 原文地址:https://www.cnblogs.com/BeautifulWater/p/15040250.html
Copyright © 2011-2022 走看看