P1330 封锁阳光大学

01染色,取染色个数较小的。
注意图不一定联通。

#include<cstdio>
#include<iostream>
#include<cstring>
using namespace std;
const int N=100005;
int n,m;
int head[N];
int c[N];
bool vis[N]; 
int sum[2];
int tot,ans;
int read(){
	int num=0,f=1;
	char c=getchar();
	while(c<'0'||c>'9'){
		if(c=='-') f=-1;
		c=getchar();
	}
	while(c>='0'&&c<='9'){
		num=num*10+c-'0';
		c=getchar();
	}
	return num*f;
}
struct node{
	int to,next;
}edge[N<<1];
void add(int u,int v){
	edge[tot].to=v;
	edge[tot].next=head[u];
	head[u]=tot++;
}
bool dfs(int u,int color){
	if(vis[u]){
		if(color!=c[u]) return 0;
		return 1;
	}
	vis[u]=1;
	c[u]=color;
	sum[color]++;
	bool flag=0;
	for(int i=head[u];i!=-1;i=edge[i].next){
		int v=edge[i].to;
		if(!dfs(v,1-color)){
			return 0;
		}
	}
	return 1;
}
int main(){
	memset(head,-1,sizeof(head));
	n=read(); m=read();
	for(int i=1;i<=m;i++){
		int u=read(),v=read();
		add(u,v); add(v,u);
	}
	for(int i=1;i<=n;i++){
		if(vis[i]) continue;
		if(!vis[i]){
			sum[0]=sum[1]=0;
			if(!dfs(i,0)){
				printf("Impossible\n");
				return 0;
			}
			ans+=min(sum[1],sum[0]);
		}
	}
	printf("%d",ans);
	return 0;
}
posted @ 2021-09-11 19:48  dfydn  阅读(24)  评论(0编辑  收藏  举报