题目描述
题目来源 :LeetCode 第 5 题
标签:字符串、动态规划、中心扩展
题目要求 :
给你一个字符串
s,找到s中最长的回文子串。
什么是回文串?
如果一个字符串正着读和反着读是一样的,那么它就是回文串。例如 "aba"、"abba" 都是回文串。
提示与约束条件:
1 <= s.length <= 1000
s仅由数字和英文字母组成
方法一:字符串反转 + 最长公共子串
1. 初始思路
回文串的特性是"正读反读都一样"。一个直观的想法是:将原字符串 s 反转得到 ss,然后寻找 s 和 ss 的最长公共子串(LCS)。这个公共子串理论上就是最长回文子串。
2. 逻辑漏洞与修正
漏洞 :仅仅寻找公共子串是不够的。例如 s = "abacdfgdcaba",反转后 ss = "abacdfgdcaba",两者的最长公共子串是 "abacd",但它并不是回文。
修正 :必须验证找到的公共子串在原字符串中的索引与反转字符串中的索引是否满足对称关系。即:若 s 中起始索引为 i,ss 中起始索引为 j,匹配长度为 len,则必须满足 i + j + len == s.size(),才能保证它是真正的回文。
3. 代码实现
cpp
class Solution {
public:
string longestPalindrome(string s) {
if (s.empty()) return "";
string ss = s;
reverse(ss.begin(), ss.end());
string ans = "";
for (int i = 0; i < s.size(); i++) {
for (int j = 0; j < ss.size(); j++) {
int len = 0;
while (i + len < s.size() && j + len < ss.size() && s[i + len] == ss[j + len]) {
len++;
}
// 核心修正:验证索引对称性
if (len > ans.size() && i + j + len == s.size()) {
ans = s.substr(i, len);
}
}
}
return ans;
}
};

复杂度分析
-
时间复杂度 :O(n3)。双层循环枚举起点为 O(n2),内部
while匹配最坏情况为 O(n)。 -
空间复杂度 :O(n)。需要存储反转字符串
s。
方法二:中心扩展法(最优解法)
1. 思路转变
放弃"反转匹配"的间接思路,回归回文的本质:对称性 。回文串一定有一个"中心",从这个中心向两边扩展,两边的字符必定相等。
中心可能有两种情况:
奇数长度 :中心是一个字符(如
"aba",中心是'b')。偶数长度 :中心是两个字符之间的空隙(如
"abba",中心在两个'b'之间)。
我们只需遍历字符串的每一个位置,将其作为中心向两边扩展,记录最长的回文即可。
2. 代码实现
cpp
class Solution {
public:
string longestPalindrome(string s) {
if (s.empty()) return "";
int start = 0, maxLen = 1;
for (int i = 0; i < s.size(); i++) {
// 奇数长度回文扩展
int len1 = expandAroundCenter(s, i, i);
// 偶数长度回文扩展
int len2 = expandAroundCenter(s, i, i + 1);
int len = max(len1, len2);
if (len > maxLen) {
maxLen = len;
start = i - (len - 1) / 2;
}
}
return s.substr(start, maxLen);
}
private:
int expandAroundCenter(const string& s, int left, int right) {
while (left >= 0 && right < s.size() && s[left] == s[right]) {
left--;
right++;
}
return right - left - 1;
}
};

复杂度分析
-
时间复杂度:O(n2)。共有 2n−1个中心,每个中心最多扩展 O(n) 次。
-
空间复杂度:O(1)。只需常数级别的额外空间,无需存储反转字符串。
总结与对比
| 方法 | 核心关键词 | 时间复杂度 | 空间复杂度 |
|---|---|---|---|
| 反转匹配法 | 反转、公共子串、索引验证 | O(n3) | O(n) |
| 中心扩展法 | 对称性、奇偶中心、双指针扩展 | O(n2) | O(1) |
