文章
14
粉丝
0
获赞
16
访问
917
#include
using namespace std;
int main()
{
int N;
string s2; cin >> N;
for(int i = 1; i <= N; i ++)
{
cin >> s2; int len2 = s2.size();
vector moshi(len2, 0);
for(int i = 1; i < len2; i ++)
{
int j = moshi[i - 1];
while(j > 0 && s2[i] != s2[j]) j = moshi[j - 1];
if(s2[i] == s2[j]) j ++;
moshi[i] = j;
} //kmp模板
int p = len2 - moshi[len2 - 1]; 如果是周期串,比如题目例子,最小前缀为长度减去moshi[len2 - 1],这里不好理解
if(moshi[len2 - 1] % p == 0) cout << p;
else cout << len2;
if(i != N) cout << '\n' << '\n';
}
}
下面是g大人给的三段解释
kmp是最长公共前缀和公共后缀相等,就是moshi[i]对应数值
假设字符串 s 是由某个长度为 p 的字符串重复得到的:
|---- p ----|---- p ----|---- p ----|
那说明:
去掉最后一个周期块,剩下的前缀
去掉第一个周期块,剩下的后缀
它们一定完全一样,长度是 n - p,所以:最长相等前后缀长度 L = n - p 反过来:p = n - L,这就是:int p = n - L;
用 HoHoHo 再验证一次:n = 6 L = 4 p = 6 - 4 = 2 而 "Ho" 的长度正好是 2
那为什么还要判断 n % p == 0?
abcab
登录后发布评论
抱歉字体乱七八糟懒得改了,感觉g大人给的这个解释挺好懂的