2-SAT

2-SAT模板

有一个问题,怎么求出字典序最小的方案?
刷题列表
link
kink2

2-sat模板

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
#include<cstdio>
#include<cstring>
#include<vector>
#include<algorithm>
using namespace std;
const int maxn = 1000*2+100;
struct TwoSAT
{
int n;
vector<int> G[maxn*2];//存图
int S[maxn*2],c;//dfs中的栈
bool mark[maxn*2];
bool dfs(int x)
{
if(mark[x^1]) return false;
if(mark[x]) return true;
mark[x]=true;
S[c++]=x;
for(int i=0;i<G[x].size();i++)
if(!dfs(G[x][i])) return false;
return true;
}
void init(int n)
{
this->n=n;
for(int i=0;i<2*n;i++) G[i].clear();
memset(mark,0,sizeof(mark));
}
//xval表示的是偏移
void add_clause(int x,int xval,int y,int yval)
{
x=x*2+xval;
y=y*2+yval;
G[x].push_back(y);
}
bool solve()
{
for(int i=0;i<2*n;i+=2)
if(!mark[i] && !mark[i+1])
{
c=0;
if(!dfs(i))
{
while(c>0) mark[S[--c]]=false;
if(!dfs(i+1)) return false;
}
}
return true;
}
}TS;

poj 3648 wedding

思路来源
这道题目的建图很巧妙啊,注意一开始我们规定妻子一定是在左边的,那个连图的细想很巧妙

对于第i对夫妻来说,妻子的编号编号是u=2\i, 丈夫的编号是v=2\i+1,
mark[u]=true表示妻子在左边,mark[u+1]=true表示妻子在右边
mark[v]=true表示丈夫在左边,同理相似的方法表示在右边

未解决的问题

文章目录
  1. 1. 2-sat模板
  2. 2. poj 3648 wedding
  3. 3. 未解决的问题
{{ live2d() }}