2. 暴力求解
#include <iostream>
#include <string>
#include <algorithm>
using namespace std;
int main() {
string s;
cin >> s;
int n = s.size();
if (n <= 1) return n;
int ans = 0;
int st = 0;
for (int i = 0; i < n; i++) {
for (int j = i; j < n; j++) {
string substr = s.substr(i, j - i + 1);
string tmp = substr;
reverse(tmp.begin(), tmp.end());
if (tmp == substr && tmp.size() > ans) {
st = i;
ans = tmp.size();
}
}
}
cout << ans << endl;
}
时间复杂度:O(N2)
2. 中心扩散方法
class Solution {
public:
string longestPalindrome(string s) {
int n = s.size();
if (n <= 1) return s;
int left = 0, right = 0, maxlen = 0, st = 0;
for(int i = 0; i < n; i++) {
left = i - 1;
right = i + 1;
int len = 1;
while(left >= 0 && s[left] == s[i]) {
left--;
len++;
}
while(right < n && s[right] == s[i]) {
right++;
len++;
}
while(left >= 0 && right < n && s[right] == s[left]) {
right++;
left--;
len = len + 2;
}
if (len > maxlen) {
maxlen = len;
st = left;
}
}
return s.substr(st+1, maxlen);
}
};
3. 动态规划
class Solution {
public:
string longestPalindrome(string s) {
int n = s.size();
if (n < 2) return s;
vector<vector<int>> dp(n, vector<int> (n, 0));
for (int i = 0; i < n; i++)
dp[i][i] = true;
int maxlen = 1;
int begin = 0;
//先枚举字符串长度
for (int L = 2; L <= n; L++) {
// 枚举位置
for (int i = 0; i < n; i++) {
int j = i + L - 1;
if (j >= n) break;
if (s[i] != s[j])
dp[i][j] = false;
else {
if (j - i <= 2) dp[i][j] = true;
else dp[i][j] = dp[i+1][j-1];
}
if (dp[i][j] && j - i + 1 > maxlen) {
maxlen = j - i + 1;
begin = i;
}
}
}
return s.substr(begin, maxlen);
}
};
得到所有回文子串
class Solution {
public:
int countSubstrings(string s) {
int n = s.size();
int ans = 0;
// 遍历所有回文中心
for (int i = 0; i < 2 * n - 1; i++) {
int l = i / 2, r = l + i % 2;
while ( l >= 0 && r < n && s[l] == s[r]) {
l--;
r++;
ans++;
}
}
return ans;
}
};