POJ 3678 2-sat,基礎題

鏈接:http://poj.org/problem?id=3678

代碼:

#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#include <vector>
#include <queue>
#include <stack>
#include <set>
#include <map>
#include <string>
#include <cmath>
#include <cstdlib>
#include <ctime>
using namespace std;
#define mem(a,b) memset((a),(b),sizeof((a)))

void RI (int& x){
    x = 0;
    char c = getchar ();
    while (c == ' '||c == '\n')    c = getchar ();
    bool flag = 1;
    if (c == '-'){
        flag = 0;
        c = getchar ();
    }
    while (c >= '0' && c <= '9'){
        x = x * 10 + c - '0';
        c = getchar ();
    }
    if (!flag)    x = -x;
}
void RII (int& x, int& y){RI (x), RI (y);}
void RIII (int& x, int& y, int& z){RI (x), RI (y), RI (z);}

const int maxn = 2100;
int n,m;
struct Side{
    int v,next;
}side[maxn*maxn];
int top,node[maxn];
int t,dfn[maxn],low[maxn],sum;
stack<int>s;
void add_side(int u,int v){
    side[top] = (Side){v,node[u]};
    node[u] = top++;
}
void init(){
    memset(node,-1,sizeof(node));
    memset(dfn,0,sizeof(dfn));
    top=sum=t=0;
}
void dfs(int u){
    dfn[u]=low[u]=++t;
    s.push(u);
    for(int i=node[u];i!=-1;i=side[i].next){
        int v=side[i].v;
        if(!dfn[v])dfs(v);
        if(dfn[v]!=-1)low[u]=min(low[u],low[v]);
    }
    if(low[u]==dfn[u]){
        int v;
        do{
            v=s.top();s.pop();
            dfn[v]=-1;
            low[v]=sum;
        }while(v!=u);
        sum++;
    }
}
bool solve(){
    for(int i=0;i<n;i++)//判斷是否有可行解
        if(low[2*i]==low[2*i+1])return false;
    return true;
}
int main()
{
    while(~scanf("%d%d",&n,&m)){
        init();
        while(m --){
            int a,b,c,fa,fb;
            char op[5];
            RIII(a,b,c);
            scanf("%s",op);
            a *= 2;b *= 2;
            fa = a + 1;fb = b + 1;
            if(op[0] == 'A'){
                if(c == 1){
                    add_side(a,fa);
                    add_side(b,fb);
                }
                else {
                    add_side(fa,b);
                    add_side(fb,a);
                }
            }
            else if(op[0] == 'O'){
                if(c == 1){
                    add_side(a,fb);
                    add_side(b,fa);
                }
                else {
                    add_side(fa,a);
                    add_side(fb,b);
                }
            }
            else {
                if(c == 1){
                    add_side(a,fb);
                    add_side(fa,b);
                    add_side(fb,a);
                    add_side(b,fa);
                }
                else {
                    add_side(a,b);
                    add_side(fa,fb);
                    add_side(b,a);
                    add_side(fb,fa);
                }
            }
        }
        for(int i=0;i<2*n;i++)
            if(!dfn[i])dfs(i);
        if(!solve())cout<<"NO"<<endl;
        else cout<<"YES"<<endl;
    }
    return 0;
}


發佈了140 篇原創文章 · 獲贊 5 · 訪問量 7萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章