BZOJ1398Vijos1382寻找主人 Necklace——最小表示法
题目描述
给定两个项链的表示,判断他们是否可能是一条项链。
输入
输入文件只有两行,每行一个由0至9组成的字符串,描述一个项链的表示(保证项链的长度是相等的)。
输出
如果两条项链不可能同构,那么输出’No’,否则的话,第一行输出一个’Yes’
第二行输出该项链的字典序最小的表示。 设L = 项链长度,L <= 1000000。
样例输入
2234342423
2423223434
2423223434
样例输出
Yes
2234342423
2234342423
判断两个字符串是否循环同构只要将两个字符串的最小循环同构串找到判断是否相同即可,分别用最小表示法求一下即可。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 | #include<set> #include<map> #include<queue> #include<stack> #include<cmath> #include<cstdio> #include<vector> #include<bitset> #include<cstring> #include<iostream> #include<algorithm> #define ll long long using namespace std; int n,m; char s[2000010]; char t[2000010]; int find( char *s, int n) { int l=1; int r=2; while (l<=n&&r<=n) { if (s[l]<s[r]) { r++; } else if (s[l]>s[r]) { l=r++; } else { int k; for (k=1;k<n;k++) { if (s[l+k]>s[r+k]) { l=r++; break ; } else if (s[l+k]<s[r+k]) { r=r+k+1; break ; } } } } return l; } int main() { scanf ( "%s%s" ,s+1,t+1); int len= strlen (s+1); for ( int i=len+1;i<=2*len;i++) { s[i]=s[i-len]; t[i]=t[i-len]; } n=find(s,len); m=find(t,len); for ( int i=n,j=m;len--;i++,j++) { if (s[i]!=t[j]) { printf ( "No" ); return 0; } } len= strlen (s+1)/2; printf ( "Yes\n" ); for ( int i=n;i-n+1<=len;i++) { printf ( "%c" ,s[i]); } } |
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步