1 /** 2 *2-SAT模板,Modified Edition of LRJ 3 *输入:按照法则添加边(参数为2*i或者2*i+1) 4 *运行:先init(n),再add(),再solve() 5 *输出:mark[](1表示选中),solve()(是否有解) 6 */ 7 const int maxn = 0; 8 struct TwoSAT 9 { 10 int n; 11 vector<int> G[maxn*2]; 12 bool mark[maxn*2]; 13 int S[maxn*2], c; 14 15 bool dfs(int x) 16 { 17 if (mark[x^1]) return false; 18 if (mark[x]) return true; 19 mark[x] = true; 20 S[c++] = x; 21 for (int i = 0; i < G[x].size(); i++) 22 if (!dfs(G[x][i])) return false; 23 return true; 24 } 25 26 void init(int n) 27 { 28 this->n = n; 29 for (int i = 0; i < n*2; i++) G[i].clear(); 30 memset(mark, 0, sizeof(mark)); 31 } 32 33 /// x AND y = 1 34 void add_and_one(int x,int y) 35 { 36 G[x^1].push_back(y); 37 G[y^1].push_back(x); 38 G[x].push_back(y); 39 G[y^1].push_back(x^1); 40 G[y].push_back(x); 41 G[x^1].push_back(y^1); 42 } 43 44 /// x AND y = 0 45 void add_and_zero(int x,int y) 46 { 47 G[x].push_back(y^1); 48 G[y].push_back(x^1); 49 } 50 51 /// x OR y = 1 52 void add_or_one(int x,int y) 53 { 54 G[x^1].push_back(y); 55 G[y^1].push_back(x); 56 } 57 58 /// x OR y = 0 59 void add_or_zero(int x,int y) 60 { 61 G[x].push_back(y^1); 62 G[y].push_back(x^1); 63 G[x].push_back(y); 64 G[y^1].push_back(x^1); 65 G[x^1].push_back(y^1); 66 G[y].push_back(x); 67 } 68 69 /// x XOR y = 1 70 void add_xor_one(int x,int y) 71 { 72 G[x^1].push_back(y); 73 G[y^1].push_back(x); 74 G[x].push_back(y^1); 75 G[y].push_back(x^1); 76 } 77 78 /// x XOR y = 0 79 void add_xor_zero(int x,int y) 80 { 81 G[x^1].push_back(y^1); 82 G[y].push_back(x); 83 G[x].push_back(y); 84 G[y^1].push_back(x^1); 85 } 86 87 /// x -> y 88 void add_to(int x,int y) 89 { 90 G[x].push_back(y); 91 G[y^1].push_back(x^1); 92 } 93 94 bool solve() 95 { 96 for(int i = 0; i < n*2; i += 2) 97 if(!mark[i] && !mark[i+1]) 98 { 99 c = 0; 100 if(!dfs(i)) 101 { 102 while(c > 0) mark[S[--c]] = false; 103 if(!dfs(i+1)) return false; 104 } 105 } 106 return true; 107 } 108 };