poj 3648

2sat,注意题意。

代码:

#include<iostream>
#include<fstream>

using namespace std;

struct e{
	int data;
	e *next;
}edge[121],edge2[122];
int n,m;

int v[121],low[121],dfn[121],stack[121],scc[121],tot,index,top;

void tarjan(int s){
	int i,j,k;
	dfn[s]=low[s]=++index;
	stack[++top]=s;
	v[s]=1;
	e *p=edge[s].next;
	while(p){
		if(dfn[p->data]==0)
		{
			tarjan(p->data);
			low[s]=min(low[s],low[p->data]);
		}
		else
			if(v[p->data])
			{
				low[s]=min(low[s],dfn[p->data]);
			}
		p=p->next;
	}
	if(low[s]==dfn[s]){
		++tot;
		
		do{
			i=stack[top--];
			scc[i]=tot;
			
			v[i]=0;
		}while(i!=s);
	}
}



void solve(){
	int i,j,k;
	index=0;tot=0;top=0;
	memset(v,0,sizeof(v));
	memset(dfn,0,sizeof(dfn));
	for(i=0;i<4*n;i++)
		if(dfn[i]==0)
			tarjan(i);
}

void build(){
	int i,j,k;
	memset(edge2,0,sizeof(edge2));
	for(i=0;i<4*n;i++)
	{
		e *p=edge[i].next;
		while(p){
			if(scc[p->data]!=scc[i])
			{
				e *q=new e;
				q->data=scc[i];
				q->next=edge2[scc[p->data]].next;
				edge2[scc[p->data]].next=q;
			}
			p=p->next;
		}
	}
}

int queue[130];

void dfs(int s){
	int i,j,k;
	v[s]=1;
	e *p=edge2[s].next;
	while(p){
		if(v[p->data]==0)
			dfs(p->data);
		p=p->next;
	}
	queue[top++]=s;
}

int ant[130];

void solve1(){
	int i,j,k;
	for(i=0;i<2*n;i++)
	{
		ant[scc[i]]=scc[i+2*n];
		ant[scc[i+2*n]]=scc[i];
	}
	build();
	top=0;
	for(i=0;i<tot;i++)
		if(v[i]==0)
			dfs(i);
	memset(v,0,sizeof(v));
	for(i=top-1;i>=0;i--)
	{
		j=queue[i];
		if(v[j]==0)
		{
			v[j]=1;
			v[ant[j]]=2;
			j=ant[j];
			e *p=edge2[j].next;
			while(p){
				v[p->data]=2;
				p=p->next;
			}
		}
	}
	for(i=1;i<n;i++)
		if(v[scc[i]]==1)
			cout<<i<<"w ";
	for(i=n;i<2*n;i++)
		if(v[scc[i]]==1)
			cout<<i-n<<"h ";
	cout<<endl;
}
		
void read(){
//	ifstream cin("in.txt");
	int i,j,k,s;
	while(1){
		cin>>n>>m;
		if(n==0&&m==0) return;
		memset(edge,0,sizeof(edge));
		s=2*n;

		e *p=new e;
		p->data=0;
		p->next=edge[n].next;
		edge[n].next=p;

		e *q=new e;
		q->data=3*n;
		q->next=edge[2*n].next;
		edge[2*n].next=q;

		for(i=0;i<n;i++)
		{
			e *p=new e;
			p->data=i+s;
			p->next=edge[i+n].next;
			edge[i+n].next=p;
			
			e*q=new e;
			q->data=i;
			q->next=edge[i+n+s].next;
			edge[i+n+s].next=q;

			e*p1=new e;
			p1->data=i+n;
			p1->next=edge[i+s].next;
			edge[i+s].next=p1;

			e *q1=new e;
			q1->data=i+n+s;
			q1->next=edge[i].next;
			edge[i].next=q1;
		}
		char c1,c2;
		for(i=1;i<=m;i++)
		{
			cin>>j>>c1>>k>>c2;
			if(c1=='h') j+=n;
			if(c2=='h') k+=n;
			e *p=new e;
			p->data=k;
			p->next=edge[j+s].next;
			edge[j+s].next=p;

			e *q=new e;
			q->data=j;
			q->next=edge[k+s].next;
			edge[k+s].next=q;
		}
		solve();
		for(i=1;i<=n*2;i++)
			if(scc[i]==scc[i+s])
				break;
		if(i<=n*2)
		{
			cout<<"bad luck"<<endl;
			continue;
		}
		else
		{
			solve1();
			
		}
	}
}

int main(){
	read();
	return 0;
}

posted on 2011-03-19 18:03  宇宙吾心  阅读(500)  评论(0编辑  收藏  举报

导航