HDU 3062 Party

2-sat 入门题

《由对称性解2-SAT问题》

#include <iostream>
#include <cstdio>
#include <cstring>
#include <vector>
#include <stack>
using namespace std;
const int N = 2010;
vector<int> vec[N];
int n, m, id, cnt;
int dfn[N], vis[N], low[N], belong[N];
stack<int> s;
void init(){
	memset(vis,0,sizeof(vis));
	memset(dfn,-1,sizeof(dfn));
	memset(low,-1,sizeof(low));
	memset(belong,-1,sizeof(belong));
	id = cnt = 0;
	while(!s.empty())s.pop();
	for(int i = 0; i < 2*n; i++)vec[i].clear();
}
void tarjan(int u){
	dfn[u] = low[u] = id++;
	vis[u] = 1;
	int sz = vec[u].size();
	s.push(u);
	for(int i = 0; i < sz; i++){
		int v = vec[u][i];
		if(dfn[v] == -1){
			tarjan(v);
			low[u] = min(low[u], low[v]);
		}
		else if(vis[v] == 1){
			low[u] = min(low[u], dfn[v]);
		}
	}
	if(low[u] == dfn[u]){
		cnt++;
		while(!s.empty()){
			int temp = s.top();
			s.pop();
			vis[temp]=0;
            belong[temp]=cnt;
			if(temp == u)break;
		}
	}
}
int main(){
	int a,b,c,d;
	while(~scanf("%d%d", &n, &m)){
			init();
		for(int i = 0; i < m; i++){
			scanf("%d%d%d%d", &a, &b, &c, &d);
			vec[2*a+c].push_back(2*b+1-d);
			vec[2*b+d].push_back(2*a+1-c);
		}
		for(int i = 0; i < 2*n; i++){
			if(dfn[i] == -1)tarjan(i);
		}
		bool flag = true;
		for(int i  = 0; i < n; i++){
			if( belong[2*i] == belong[2*i+1] ){
				flag=false;
				break;
			}
		}
		puts(flag?"YES":"NO");
	}
	return 0;
}


你可能感兴趣的:(HDU,2-sat)