Play on Words UVA
阿新 • • 發佈:2018-12-11
Play on Words
題意:給出一些單詞,問能否讓首尾字母相同的字串相連,最後形成一個串。
思路:不難看出,這是一個尤拉道路問題。
簡單介紹一下尤拉道路:
在尤拉道路中,除了起點和終點,所有的點的入度和出度都相等。(如所有的點的入度都等於出度,那麼就形成歐拉回路)並且整幅圖是聯通的,那麼這就形成了歐拉回路、道路。
是否聯通,我們通常通過並查集判斷。
AC程式碼:
#include<cstdio> #include<iostream> #include<map> #include<vector> #include<cstring> using namespace std; int ind[30]; int outd[30]; int fa[30]; void init() { for(int i=0;i<26;i++) { fa[i]=i; } } int find(int x) { return x==fa[x]?x:fa[x]=find(fa[x]); } void merge(int x,int y) { int fx=find(x); int fy=find(y); fa[fy]=fx; } int main() { int t; scanf("%d",&t); while(t--) { memset(ind,0,sizeof(ind)); memset(outd,0,sizeof(outd)); int n; scanf("%d",&n); init(); for(int i=0;i<n;i++) { char s[1005]; scanf("%s",s); int u=s[0]-'a'; int v=s[strlen(s)-1]-'a'; ind[v]++,outd[u]++; merge(u,v); } vector<int> ans; int flag=1; int cnt=0; for(int i=0;i<26;i++) { if(ind[i]!=outd[i]) { ans.push_back(i); } if(ans.size()>2) {flag=0;break;} if((ind[i]||outd[i])&&fa[i]==i){cnt++;} if(cnt>1){flag=0;break;} } if(ans.size()==2) { int a=ans[0],b=ans[1]; if(ind[a]+ind[b]==outd[a]+outd[b]&&(outd[a]-ind[a]==1||outd[a]-ind[a]==-1)) { flag=1; } else flag=0; } if(!flag) cout<<"The door cannot be opened."<<endl; else cout<<"Ordering is possible."<<endl; } }