hdu5285-wyh2000 and pupil-(染色法二分图判定)
Posted shoulinniao
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了hdu5285-wyh2000 and pupil-(染色法二分图判定)相关的知识,希望对你有一定的参考价值。
http://acm.hdu.edu.cn/showproblem.php?pid=5285
题意:把互不认识的人分到两个组,第一组人数尽可能多。
题解:把互不认识的人连起来,当作二分图,二分图可能有多个,对于没有连线的点,扔到第一个图里。二色法对每个二分图染色,记录每个图比较多的颜色的数量累计到答案里。
特判坑:n<=1 或者 m==0
#include<stdio.h> #include<iostream> #include<algorithm> #include<cstring> #include<math.h> #include<string> #include<map> #include<queue> #include<stack> #include<set> #define ll long long #define inf 0x3f3f3f3f using namespace std; int n,m; vector<int>a[100005]; int color[100005]; int zero,one; int minn,maxx; bool flag; void bfs(int x) queue<int>que;///对x点进行广搜,二色法,一个标记为0,另一个标记为1 zero=one=0; zero++; que.push(x); color[x]=0; while(!que.empty()&&flag) int now=que.front(); que.pop(); int c=color[now]; int len=a[now].size(); for(int i=0;i<len;i++) int next=a[now][i]; if(color[next]==-1)///如果没有被染色过, que.push(next); if(c==0) color[next]=1,one++; else color[next]=0,zero++; else ///被染色过 if( color[next]==c ) flag=false; break; int main()//hdu5285 int t; scanf("%d",&t); while(t--) scanf("%d%d",&n,&m); for(int i=1;i<=n;i++) a[i].clear(); memset(color,-1,sizeof(color)); minn=maxx=0; flag=true; if(n<=1) printf("Poor wyh\n"); continue; if(m==0)///特判,否则全部染成0色 printf("%d 1\n",n-1); continue; while(m--) int u,v; scanf("%d%d",&u,&v); a[u].push_back(v); a[v].push_back(u); int no=0;///没有被染色的点,其中第一组尽量多,则把没有染色的加到多的那一边去 for(int i=1;i<=n && flag;i++) if(color[i]==-1 && a[i].size() )///没有被染色的点 并且 不是独立的 bfs(i); if(zero<one) swap(zero,one); maxx+=zero; minn+=one; else if(color[i]==-1 && a[i].size()==0)///独立的点染成颜色0,0是第一组,较多的那一组 color[i]=0; maxx++; if(flag) printf("%d %d\n",maxx,minn); else printf("Poor wyh\n"); return 0;
以上是关于hdu5285-wyh2000 and pupil-(染色法二分图判定)的主要内容,如果未能解决你的问题,请参考以下文章
hdu 5652 India and China Origins 并查集+二分