hdu1814 Peaceful Commission 2-SAT

2-SAT裸题

如果选u则必选v', 如果选v则必选u',连边即可。

#include <iostream>
#include <cstring>
#include <cstdio>
using namespace std;
struct Edge{
	int too, nxt;
}edge[40005];
int n, m, uu, vv, hea[16005], cnt, val, ans[16005], bel[16005];
void add_edge(int fro, int too){
	edge[++cnt].nxt = hea[fro];
	edge[cnt].too = too;
	hea[fro] = cnt;
}
inline int f(int x){
	return x%2==1?x+1:x-1;
}
bool pnt(int x){
	if(bel[x])	return bel[x]==1;
	bel[x] = 1;
	bel[f(x)] = 2;
	ans[++val] = x;
	for(int i=hea[x]; i; i=edge[i].nxt)
		if(!pnt(edge[i].too))
			return false;
	return true;
}
bool work(){
	for(int i=1; i<=n+n; i++){
		if(bel[i])
			continue;
		val = 0;
		if(!pnt(i)){
			for(int j=1; j<=val; j++)
				bel[ans[j]] = bel[f(ans[j])] = 0;
			if(!pnt(f(i)))	return false;
		}
	}
	return true;
}
int main(){
	while(scanf("%d %d", &n, &m)!=EOF){
		memset(hea, 0, sizeof(hea));
		memset(bel, 0, sizeof(bel));
		cnt = 0;
		for(int i=1; i<=m; i++){
			scanf("%d %d", &uu, &vv);
			add_edge(uu, f(vv));
			add_edge(vv, f(uu));
		}
		if(work()){
			for(int i=1; i<=n+n; i++)
				if(bel[i]==1)
					printf("%d
", i);
		}
		else	printf("NIE
");
	}
	return 0;
}
原文地址:https://www.cnblogs.com/poorpool/p/8005706.html