题目连接:https://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=1070
将每个单词首字母和尾字母抽象成两个点,中间一条有向边
判断是否存在欧拉路径
存在欧拉路径的条件:
1、图连通
2、有一个节点入度比出度大1,一个节点出度比入度大1
条件一可用dfs或者并查集来做
1 #include<cstdio> 2 #include<cstring> 3 #include<set> 4 #include<iostream> 5 #include<cctype> 6 #include<string> 7 #include<sstream> 8 #include<algorithm> 9 #include<map> 10 #define LL long long 11 using namespace std; 12 int in[30],out[30]; 13 int f[30]; 14 set<int> si; 15 void init() 16 { 17 for(int i=0;i<30;i++) 18 { 19 in[i]=0; 20 out[i]=0; 21 f[i]=i; 22 } 23 } 24 25 int gf(int x) 26 { 27 return x==f[x]?x:f[x]=gf(f[x]); 28 } 29 30 void uni(int a,int b) 31 { 32 int pa=gf(a); 33 int pb=gf(b); 34 f[pa]=pb; 35 } 36 string s; 37 int main() 38 { 39 int t; 40 scanf("%d",&t); 41 while(t--) 42 { 43 int ok=1; 44 si.clear(); 45 init(); 46 int n; 47 int a,b; 48 int ctin=0,ctout=0,ct=0; 49 scanf("%d",&n); 50 for(int i=0;i<n;i++) 51 { 52 cin>>s; 53 a=s[0]-'a'; 54 b=s[s.length()-1]-'a'; 55 si.insert(a); 56 si.insert(b); 57 in[a]++; 58 out[b]++; 59 if(gf(a)!=gf(b)) uni(a,b); 60 } 61 int u=gf(a); 62 for(set<int> ::iterator it=si.begin();it!=si.end();it++) 63 { 64 if(gf(*it)!=u) {ok=0;break;} 65 if(in[*it]-out[*it]==1) ctin++; 66 else if(in[*it]-out[*it]==-1) ctout++; 67 else if(in[*it]-out[*it]>1||in[*it]-out[*it]<-1) {ok=0;break;} 68 if(ctin>1||ctout>1) {ok=0;break;} 69 } 70 if(ok) puts("Ordering is possible."); 71 else puts("The door cannot be opened."); 72 } 73 }