給定字符串 S(長度 ≤ 1000),找出最長回文子串。假設唯一解。
枚舉所有子串長度(從長到短)、起始位置,判斷是否回文。超時。
dp[i][j] 表示 s[i..j] 是否回文。狀態轉移:dp[i][j] = (s[i]==s[j]) && dp[i+1][j-1]。空間超限(Memory Limit Exceeded)。
回文中心有 2n-1 種可能(n 個字符中心 + n-1 個間隙中心)。對每個中心向兩側擴展,記錄最長。
longest.length()) longest = p1;
String p2 = expand(s, i, i + 1); // 偶數長,中心在間隙
if (p2.length() > longest.length()) longest = p2;
}
return longest;
}
private String expand(String s, int l, int r) {
while (l >= 0 && r < s.length() && s.charAt(l) == s.charAt(r)) {
l--; r++;
}
return s.substring(l + 1, r); // 回文實際範圍 [l+1, r-1]
}
}
= 0 && r < s.size() && s[l] == s[r]) { l--; r++; }
int len = r - l - 1;
if (len > bestLen) { bestLen = len; bestL = l + 1; }
};
for (int i = 0; i < s.size(); ++i) {
expand(i, i);
expand(i, i + 1);
}
return s.substr(bestL, bestLen);
}
| 方法 | 時間 | 空間 | 備註 |
|---|---|---|---|
| 暴力 | O(n³) | O(1) | 教學用 |
| DP | O(n²) | O(n²) | 空間超限 |
| 中心擴展 | O(n²) | O(1) | 工程首選 |
| Manacher | O(n) | O(n) | 最優但複雜 |