L2-008 longest substring symmetry (25 minutes)
For a given string, this question requires you to output the length of the longest substring symmetrical. For example, given Is PAT&TAP symmetric?
the longest substring of symmetry s PAT&TAP s
, so you should output 11.
Input formats:
Input gives the length of not more than 1000 non-empty string in a row.
Output formats:
Symmetrical output longest substring of length in a row.
Sample input:
Is PAT&TAP symmetric?
Sample output:
11
Thinking: Manacher time complexity of O (n) solving palindromic longest substring.
#include <iostream>
#include <cstring>
#include <algorithm>
using namespace std;
string s;
char s_new[4000];
int p[5000];
int Init(){
int len = s.length();
s_new[0] = '$';
s_new[1] = '#';
int j = 2;
for (int i = 0; i < len; i++){
s_new[j++] = s[i];
s_new[j++] = '#';
}
s_new[j] = '\0'; // 别忘了哦
return j; // 返回 s_new 的长度
}
int Manacher(){
int len = Init(); // 取得新字符串长度并完成向 s_new 的转换
int max_len = -1; // 最长回文长度
int id;
int mx = 0;
for (int i = 1; i < len; i++){
if (i < mx)
p[i] = min(p[2 * id - i], mx - i); // 需搞清楚上面那张图含义, mx 和 2*id-i 的含义
else
p[i] = 1;
while (s_new[i - p[i]] == s_new[i + p[i]]) // 不需边界判断,因为左有'$',右有'\0'
p[i]++;
// 我们每走一步 i,都要和 mx 比较,我们希望 mx 尽可能的远,这样才能更有机会执行 if (i < mx)这句代码,从而提高效率
if (mx < i + p[i]) {
id = i;
mx = i + p[i];
}
max_len = max(max_len, p[i] - 1);
}
return max_len;
}
int main(){
getline(cin, s);
printf("%d\n", Manacher());
return 0;
}
Dynamic Programming:
Analysis: There are two possibilities, ⼀ kind of back to the file is ⻓ string is odd, ⼀ species is an even number. the subscript i is the current character string.
When the back is an odd number when the file string, j denotes the i ij ⻓ string files back configuration of j +; ⻓ string when the back of the file is an even number, j represents
i + 1 j characters left ⼀ back to the file of the string ⻓ the right until i j characters ~
Use maxvalue, the maximum values and save the resulting output traversal ~
#include <iostream>
using namespace std;
int main() {
string s;
getline(cin, s);
int maxvalue = 0, temp;
int len = s.length();
for( int i = 0; i < len; i++) {
temp = 1;
for( int j = 1; j < len; j++) {
if( i - j < 0 || i + j >= len || s[i - j] != s[i + j])
break;
temp += 2;
}
maxvalue = temp > maxvalue ? temp : maxvalue;
temp = 0;
for( int j = 1; j < len; j++) {
if( i - j + 1 < 0 || i + j >= len || s[i - j + 1] != s[i + j])
break;
temp += 2;
}
maxvalue = temp > maxvalue ? temp : maxvalue;
}
cout << maxvalue;
return 0;
}