并查集
View Code
1 #include <cstdio> 2 #include <algorithm> 3 #include <cstring> 4 using namespace std; 5 6 const int N=20010; 7 int set[N],key[N],n; 8 int find(int x) 9 { 10 if(x==set[x]) return x; 11 int t=find(set[x]); 12 key[x]^=key[set[x]]; 13 return set[x]=t; 14 } 15 bool merge(int x,int y,int v) 16 { 17 int fx=find(x), fy=find(y); 18 if(fx==fy) 19 { 20 return (key[x]^key[y])==v; 21 } 22 if(fy==n) swap(fx,fy); 23 set[fy]=fx; 24 key[fy]=v^key[x]^key[y]; 25 return true; 26 } 27 void query() 28 { 29 int k; 30 int p[20],fp[20]; 31 scanf("%d",&k); 32 for(int i=0;i<k;i++) 33 { 34 scanf("%d",&p[i]); 35 fp[i]=find(p[i]); 36 } 37 sort(fp,fp+k); 38 bool flag=false; 39 if(fp[k-1]!=n && k%2==1) flag=true; 40 for(int i=1;i<k;i++) 41 if(fp[i]!=fp[i-1] && i%2==1) flag=true; 42 if(flag) printf("I don't know.\n"); 43 else 44 { 45 int ans=0; 46 for(int i=0;i<k;i++) ans^=key[p[i]]; 47 printf("%d\n",ans); 48 } 49 } 50 int main() 51 { 52 int Q,C=0; 53 while((scanf("%d%d",&n,&Q)==2) && (n||Q)) 54 { 55 printf("Case %d:\n",++C); 56 for(int i=0;i<=n;i++) set[i]=i; 57 memset(key,0,sizeof(key)); 58 bool flag=false; 59 int cnt=0; 60 while(Q--) 61 { 62 char op[2]; 63 scanf("%s",op); 64 if(op[0]=='I') 65 { 66 cnt++; 67 int p,q,v; 68 char str[30]; 69 gets(str); 70 if(sscanf(str,"%d%d%d",&p,&q,&v)==2) 71 { 72 v=q; q=p; p=n; 73 } 74 if(flag) continue; 75 if(!merge(p,q,v)) 76 { 77 printf("The first %d facts are conflicting.\n",cnt); 78 flag=true; 79 } 80 } 81 else 82 { 83 if(flag) 84 { 85 int k,t; 86 scanf("%d",&k); 87 while(k--) scanf("%d",&t); 88 } 89 else query(); 90 } 91 } 92 printf("\n"); 93 } 94 return 0; 95 }