Description
小C在玩一個遊戲,在遊戲中他扮演國王的角色。國王手下有M個大臣,他們有一天對國王要處理的N件事務進行投票。每一個大臣能夠對兩件事務進行投票(同意或反對),格式以下:x c_x y c_y(x, y爲整數,c_x, c_y爲「Y」(表示同意)或「N」(表示反對)(不含雙引號),表示這個大臣對事務x的態度爲c_x,對事務y的態度爲c_y)。這些大臣很是難以對付,若是國王的決定和某個大臣的兩個意見都不一樣,那麼這個大臣就會離開國王。小C認爲不能讓任何一個大臣離開國王,不然國王就沒法正常地處理本身的事務。請你幫助小C作個決定。
Input
第一行,兩個整數N, M。
接下來的M行,每行表示一個大臣的投票。
接下來的M行,每行表示一個大臣的投票。
Output
若是小C不管如何都只能讓至少一個大臣離開國王,則輸出「IMPOSSIBLE」(不含雙引號),不然輸出一個長度爲N的字符串,若是第i件事務必須同意,則第i個字符爲「Y」;若是第i件事務必須反對,則第i個字符爲「N」,不然第i個字符爲「?」。
Sample Input
3 4
1 Y 2 N
1 N 2 N
1 Y 3 Y
1 Y 2 Y
Sample Output
YN?
Data Constraint
對於50%的數據,1<=N<=10,1<=M<=40;
對於所有的數據,1<=N<=1000,1<=M<=4000。
對於所有的數據,1<=N<=1000,1<=M<=4000。
題解
-
就是一道2-SAT問題ios
-
點u->v表明u發生則v必然發生spa
-
每個條件能夠拆爲這樣的兩個條件code
-
如1 Y 2 N 對應的是 1N->2N 2Y->1Yblog
-
咱們把1Y 1N稱爲對立節點遊戲
-
那麼咱們怎麼找到將它們連起來且沒有對立節點的路徑(就是能夠找到一條路徑,由於對立節點沒有邊相連)事件
-
能夠用dfs解決。事務
-
若是對某個事務同意就必須對該事務反對(記爲事件A),且對某個事務反對就必須對該事務同意(記爲事件B)ip
-
則不可能知足全部條件字符串
-
不然: 若事件A成立,則對該事務必須反對 get
-
若事件B成立,則對該事務必須同意
代碼
1 #include<cstdio> 2 #include<iostream> 3 #include<algorithm> 4 #include<memory.h> 5 using namespace std; 6 int next[16011],last[16011],head[16011]; 7 int f[16011],k[16022][3],n,m,x,z,num,tot; 8 bool flag,must[16011][3]; 9 void insert(int x,int y) 10 { 11 next[++tot]=head[x]; 12 head[x]=tot; 13 last[tot]=y; 14 } 15 void dfs(int x) 16 { 17 if (flag==false) return; 18 f[x]=num; 19 if (f[x]==num&&f[x^1]==num) flag=false; 20 if (flag==false) return; 21 int i=head[x],j; 22 while (i!=0) 23 { 24 j=last[i]; 25 if (f[j]!=num) dfs(j); 26 i=next[i]; 27 } 28 29 } 30 int main() 31 { 32 scanf("%d%d",&n,&m); 33 char ch; 34 memset(must,true,sizeof(must)); 35 for (int i=1;i<=m;i++) 36 { 37 scanf("%d",&x); 38 while(ch=getchar(),ch!='Y'&&ch!='N'); 39 if (ch=='Y') z=1; else z=0; 40 if (z==1) k[i][1]=x*2+1; else k[i][1]=x*2; 41 scanf("%d",&x); 42 while(ch=getchar(),ch!='Y'&&ch!='N'); 43 if (ch=='Y') z=1; else z=0; 44 if (z==1) k[i][2]=x*2+1; else k[i][2]=x*2; 45 insert(k[i][2]^1,k[i][1]); 46 insert(k[i][1]^1,k[i][2]); 47 } 48 for (int i=1;i<=n;i++) 49 { 50 flag=true; 51 num++; 52 f[2*i]=num; 53 dfs(2*i); 54 if (flag==false) must[i][2]=false; 55 flag=true; 56 num++; 57 f[2*i+1]=num; 58 dfs(2*i+1); 59 if (flag==false) must[i][1]=false; 60 } 61 flag=true; 62 for (int i=1;i<=n;i++) if (must[i][1]==false&&must[i][2]==false) flag=false; 63 if (flag==false) printf("IMPOSSIBLE\n"); 64 else 65 for (int i=1;i<=n;i++) 66 { 67 if (must[i][2]==true&&must[i][1]==true) printf("?"); 68 if (must[i][2]==false&&must[i][1]==true) printf("Y"); 69 if (must[i][2]==true&&must[i][1]==false) printf("N"); 70 } 71 return 0; 72 }