题目:
给定一个字符串S,请将S分割成一些子串,使每个子串都是回文串,返回S所有可能的分割方案

方法一:回溯+深度优先搜索
1. 主要思想
- 使用 深度优先搜索(DFS) 遍历
s的所有可能划分方式。 - 使用 回溯(Backtracking)尝试所有可能的子串分割,并在搜索失败时撤销上一步决策。
- 剪枝优化:如果某个子串不是回文,就直接跳过,减少不必要的递归调用。
以 "aab" 为例,我们一步步拆解执行过程:
(1) 递归函数 dfs(i)
dfs(i)代表从索引i开始尝试分割s[i:]。- 终止条件:当
i == n(遍历完整个字符串),说明找到了一个完整的回文划分,将path复制到ans中。
(2) 遍历所有可能的子串
- 设
j为子串s[i:j+1]的结束索引:- 如果
s[i:j+1]是回文,则递归处理s[j+1:]。 - 如果
s[i:j+1]不是回文,就跳过这个分割。
- 如果
Step 1: dfs(0)
i = 0,遍历j从0到2:s[0:1] = "a"是回文 → 加入path→dfs(1)s[0:2] = "aa"是回文 → 加入path→dfs(2)s[0:3] = "aab"不是回文 → 跳过
Step 2: dfs(1)(继续从 "a" 后开始)
i = 1,遍历j从1到2:s[1:2] = "a"是回文 → 加入path→dfs(2)
Step 3: dfs(2)(继续从 "a" 后开始)
i = 2,遍历j从2到2:s[2:3] = "b"是回文 → 加入path→dfs(3)
Step 4: dfs(3)(终止条件)
i = 3 == len(s),找到一个完整的划分["a", "a", "b"],存入ans,然后回溯。
4. 回溯过程
- 回溯到
dfs(2),撤销"b",继续找其他可能(没有)。 - 回溯到
dfs(1),撤销"a",尝试"aa":"aa"是回文 →dfs(2)- 继续拆分
s[2:3] = "b",得到["aa", "b"],存入ans。
最终 ans = [["a", "a", "b"], ["aa", "b"]]。
class Solution(object):
def partition(self, s):
"""
:type s: str
:rtype: List[List[str]]
"""
n=len(s) #字符串的长度
ans=[] #存储所有符合条件的回文子串分割方案
path=[] #存储当前的分割方案,DFS过程中会不断更新
def dfs(i):
if i==n: #被分割完毕
ans.append(path[:]) #复制
return
for j in range(i,n):
t=s[i:j+1] #t是s的子串,索引 i 到 j
if t==t[::-1]: #生成t的逆序,判断是否为回文
path.append(t)#将 t 加入当前分割方案
dfs(j+1)# 递归处理s[j+1:]
path.pop() #回溯
dfs(0)
return ans
时间复杂度:O(n2n),其中 n 为 s 的长度
空间复杂度:O(n)
784

被折叠的 条评论
为什么被折叠?



