Description

给出一个关系,包括 And,Xor,Or 问是否存在解.

Sol

经典的2-SAT问题.

把每个值看成两个点,一个点代表选 \(0\) ,另一个代表选 \(1\) .

首先来看 Xor :

如果两个值异或起来为 \(1\) :那么连边 \((i_0,j_1),(i_1,j_0),(j_0,i_1),(j_1,i_0)\) .

否则 连边 \((i_0,j_0),(i_1,j_1),(j_0,i_0),(j_1,i_1)\) .

然后是 And.

如果两个值 And 起来为 \(1\) :连边 \((i_0,i_1),(j_0,j_1)\)

否则 连边 \((i_1,j_0),(j_1,i_0)\)

最后是 Or.

如果两个值 Or 起来为 \(1\) :连边 \((i_0,j_1),(j_1,i_0)\)

否则 连边 \((i_1,i_0),(j_1,j_0)\) .

Tarjan 缩一下环判断一下两个点是否在一个环中就可以了.

Code

#include <cstdio>
#include <iostream>
#include <vector>
using namespace std; const int N = 2005; int n,m,cnt,cntb;
vector< int > g[N];
int d[N],b[N],ins[N];
int stk[N],top; inline int in(int x=0,char ch=getchar()){ while(ch>'9' || ch<'0') ch=getchar();
while(ch>='0' && ch<='9') x=x*10+ch-'0',ch=getchar();return x; }
void Add_Edge(int fr,int to) { g[fr].push_back(to); }
void Tarjan(int u,int fa) {
int dfsn=++cnt;d[u]=cnt,ins[u]=1,stk[++top]=u;
for(int i=0,v;i<(int)g[u].size();i++) {
v=g[u][i];
if(!d[v]) Tarjan(v,u);
if(ins[v]) d[u]=min(d[u],d[v]);
}if(dfsn==d[u]) {
for(++cntb;stk[top]!=u;top--) {
b[stk[top]]=cntb,ins[stk[top]]=0;
}ins[stk[top]]=0,b[stk[top--]]=cntb;
}
// cout<<u<<":"<<dfsn<<" "<<d[u]<<endl;
}
int main() {
// freopen("in.in","r",stdin);
n=in(),m=in();
char opt[50];
for(int i=1;i<=m;i++) {
int u=in(),v=in(),w=in();
scanf("%s",opt);
if(u>v) swap(u,v);
if(opt[0]=='X') {
if(w) {
Add_Edge(u*2,v*2+1);
Add_Edge(u*2+1,v*2);
Add_Edge(v*2,u*2+1);
Add_Edge(v*2+1,u*2);
}else {
Add_Edge(u*2,v*2);
Add_Edge(v*2,u*2);
Add_Edge(u*2+1,v*2+1);
Add_Edge(v*2+1,u*2+1);
}
}else if(opt[0]=='A') {
if(w) {
Add_Edge(u*2,u*2+1);
Add_Edge(v*2,v*2+1);
}else {
Add_Edge(u*2+1,v*2);
Add_Edge(v*2+1,u*2);
}
}else {
if(w) {
Add_Edge(u*2,v*2+1);
Add_Edge(v*2,u*2+1);
}else {
Add_Edge(u*2+1,u*2);
Add_Edge(v*2+1,v*2);
}
}
}
for(int i=0;i<2*n;i++) if(!d[i]) Tarjan(i,i);
// for(int i=0;i<2*n;i++) cout<<b[i]<<" ";cout<<endl;
for(int i=0;i<2*n;i++) if(b[i]==b[i^1]) return puts("NO"),0;
return puts("YES"),0;
}

  

最新文章

  1. 使用python crontab设置linux定时任务
  2. 关于WEB Service&amp;WCF&amp;WebApi实现身份验证之WCF篇(1)
  3. The Web server is configured to not list the contents of this directory.
  4. 【C++】array初始化0
  5. 利用less监视模式实时预览样式刷新浏览器
  6. Leetcode#76 Minimum Window Substring
  7. 浏览器解析HTML文档的资源并下载
  8. C笔记01:关于printf函数输出先后顺序的讲解
  9. android_小总结_方法过时的兼容处理
  10. linux reboot命令
  11. GDI+创建Graphics对象的2种方式
  12. js检测对象中是否存在某个属性
  13. 织梦dedecms单标签、双标签
  14. c语言第五次作业--函数
  15. redis命令详解
  16. Smarty学习笔记(二)
  17. BZOJ1467_Pku3243 clever Y_EXBSGS
  18. Hi3516EV300专业型HD IP Camera SoC
  19. codeforces16B
  20. 关于 legend_noa

热门文章

  1. ubuntu 14.04 以root权限启动chrome
  2. J2EE,J2SE,J2ME,JDK,SDK,JRE,JVM区别
  3. css设置select高度(IE,FF,Chrome)[转]
  4. 详解mysql int类型的长度值问题【转】
  5. EF6 在 SQLite中使用备忘
  6. getGlobalVisibleRect和getLocalVisibleRect
  7. java-json日期字符串转换
  8. ORACLE 中的 ROW_NUMBER() OVER() 分析函数的用法
  9. BZOJ 2120: 数颜色
  10. 【codevs1515】 跳