思路
一道裸的kmp , 不过处理next数组的时候稍微改一下 , next[i]对应的是最长匹配的前缀的下一个字母 , 方便处理和输出 。
代码
#include<iostream>
#include<cstring>
#include<cstdio>
#include<algorithm>
using namespace std ;
const int maxn = 1e5 + 10 ;
int Next[maxn] ;
char s[maxn] ;
void kmp_pre(int m){ //kmp处理
int i = 0 , j = Next[0] = -1 ;
while(i < m){
while(j != -1 && s[i] != s[j]) j = Next[j] ;
Next[++i] = ++j ; //注意这里是下一个字母 , 跟一般的next有点不一样
}
}
bool ok(int x , int m){
for(int i = x ; i < m - x ; i++)
if(Next[i] == x) return 1 ; //找到一样的前缀 输出
return 0 ;
}
int main(){
scanf("%s" , s) ;
int m = strlen(s) ;
kmp_pre(m) ;
int k = Next[m] ;
while(k != 0){
s[k] = 0 ; //方便输出 , cout输出字符串时遇到\0停止输出
if(ok(k , m)){
cout << s ;
return 0 ;
}
else k = Next[k] ;
}
}