zoukankan      html  css  js  c++  java
  • POJ3648Wedding(2sat)

    POJ 2-sat 六题之四

    http://blog.sina.com.cn/s/blog_64675f540100k1g9.html

    题目描述:

    一堆夫妇去参加一对新人的婚礼。人们坐在一个很长很长的桌子的两侧(面对面)。新郎新娘在桌子头面对面座。

    新娘不希望看见她对面的一排有一对夫妇坐着(夫妇需要分开两排座)。

    同时,一些人之间有暧昧关系,新娘也不希望有暧昧关系的人同时坐在她对面的一排。

    问你可否满足新娘的要求,可以的话,输出一种方案。

    解题报告:

    首先,每个人都可能坐在桌子两侧的某一侧,这样,把每个人拆成两个点。

    第一个点表示桌子左侧(我自己定义的),第二个表示右侧。即i和i’

    新娘我让她坐在左侧,新郎坐在右侧。

    新娘编号0,加入边i’-》i,就是说如果新娘坐右侧的话,就需要坐到左侧(这样就限定了新娘坐在左侧),新郎同样处理。

    夫妇一定一左侧,一右侧。

    有暧昧关系的人要么同时坐在左侧(不让新娘看见),要么一个坐在左侧,一个坐在右侧。

    // File Name: 3648.cpp
    // Author: zlbing
    // Created Time: 2013/1/31 0:06:20
    
    #include<iostream>
    #include<string>
    #include<algorithm>
    #include<cstdlib>
    #include<cstdio>
    #include<set>
    #include<map>
    #include<vector>
    #include<cstring>
    #include<stack>
    using namespace std;
    #define MAXN 200
    struct TwoSAT{
        int n;
        vector<int>G[MAXN*2];
        bool mark[MAXN*2];
        stack<int>S;
        bool dfs(int x)
        {
            if(mark[x^1])return false;
            if(mark[x])return true;
            mark[x]=true;
            S.push(x);
            for(int i=0;i<G[x].size();i++)
            {
                int v=G[x][i];
                if(!dfs(v))return false;
            }
            return true;
        }
        void init(int _n)
        {
            n=_n;
            for(int i=0;i<2*n;i++)
                G[i].clear();
            memset(mark,0,sizeof(mark));
        }
    /*    void add_clause(int x,int xval,int y,int yval)
        {
            x=x*2+xval;
            y=y*2+yval;
            G[x^1].push_back(y);
            G[y^1].push_back(x);
        }
    */
        void add_clause(int x,int y)
        {
            G[x].push_back(y);
        }
        bool solve()
        {
            for(int i=0;i<2*n;i=i+2)
            {
                if(!mark[i]&&!mark[i+1]){
                      while(!S.empty())
                      {
                          S.pop();
                      }
                    if(!dfs(i))
                    {
                        while(!S.empty())
                        {
                            mark[S.top()]=false;
                            S.pop();
                        }
                        if(!dfs(i+1))return false;
                    }
                }
            }
            char e;
            bool first=true;
            for(int i=4;i<4*n;i++)
                if(mark[i]){
                    int k=i/4;
                    if(i%4<2)e='w';
                    else e='h';
                    if(i%2==0){
                        if(first){
                        printf("%d%c",k,e);
                        first=false;        
                        }else 
                        printf(" %d%c",k,e);
                    }
                }
            printf("\n");
            return true;
        }
    };
    TwoSAT solver;
    int main(){
        int n,m;
        while(~scanf("%d%d",&n,&m))
        {
            solver.init(2*n);
            if(n==0&&m==0)
                break;
            int a,b;
            char cha,chb;
            solver.add_clause(1,0);
            solver.add_clause(2,3);
            for(int i=1;i<n;i++)
            {
                a=i*2,b=i*2+1;
                solver.add_clause(a*2,b*2+1);
                solver.add_clause(b*2+1,a*2);
                solver.add_clause(a*2+1,b*2);
                solver.add_clause(b*2,a*2+1);
            }
            for(int i=0;i<m;i++)
            {
                scanf("%d%c %d%c",&a,&cha,&b,&chb);
                a=cha=='w'?a*2:a*2+1;
                b=chb=='w'?b*2:b*2+1;
                solver.add_clause(a*2+1,b*2);
                solver.add_clause(b*2+1,a*2);
            }
            if(!solver.solve())
                printf("bad luck\n");
        }
        return 0;
    }
  • 相关阅读:
    浙大版《C语言程序设计(第3版)》题目集 --总结
    | C语言I作业09
    c语言课本及pta作业中运用到的程序思维
    | C语言I作业08
    团队作业(四):描述设计
    实验三《敏捷开发与XP实践》_实验报告
    MyOD(课下作业,选做)
    实验二《面向对象程序设计》_实验报告
    20175226 2018-2019-2《java程序设计》结对编程-四则运算(第二周-阶段总结)
    20175226 类定义
  • 原文地址:https://www.cnblogs.com/arbitrary/p/2883885.html
Copyright © 2011-2022 走看看