给定一个字符串 s,将 s 分割成一些子串,使每个子串都是回文串。
返回 s 所有可能的分割方案。
示例:
输入: “aab”
输出:
[
[“aa”,“b”],
[“a”,“a”,“b”]
]
方法1:回溯法
class Solution:
def partition(self, s: str) -> List[List[str]]:
if not s:
return [[]]
res = []
for i in range(len(s)):
tmp = s[:i+1]
if tmp == tmp[::-1]:
for j in self.partition(s[i+1 :]):
res.append([tmp]+ j)
return res
给定一个字符串,验证它是否是回文串,只考虑字母和数字字符,可以忽略字母的大小写。
说明:本题中,我们将空字符串定义为有效的回文串。
示例 1:
输入: “A man, a plan, a canal: Panama”
输出: true
示例 2:
输入: “race a car”
输出: false
笔记:自己写出来 做分割回文串时看到更简单的做法
解法1:
class Solution:
def isPalindrome(self, s: str) -> bool:
if not s:
return True
s1 = s.lower()
res = []
for i in s1:
if i.isalpha() or i.isdigit():
res.append(i)
if res == res[::-1]:
return True
else:
return False
解法2:
class Solution:
def isPalindrome(self, s: str) -> bool:
if not s:
return True
s1 = s.lower()
res = []
for i in s1:
if i.isalpha() or i.isdigit():
res.append(i)
if len(res)%2 == 0:
i,j = 0,len(res)-1
while i <= (len(res)/2 - 1) and j >= len(res)/2:
if res[i] != res[j]:
return False
i += 1
j -= 1
return True
else:
i,j = 0,len(res)-1
while i <= (len(res)//2 -1) and j > len(res)//2 :
if res[i] != res[j]:
return False
i += 1
j -= 1
return True
中等
给定一个非空字符串 s 和一个包含非空单词列表的字典 wordDict,判定 s 是否可以被空格拆分为一个或多个在字典中出现的单词。
说明:
拆分时可以重复使用字典中的单词。
你可以假设字典中没有重复的单词。
示例 1:
输入: s = “leetcode”, wordDict = [“leet”, “code”]
输出: true
解释: 返回 true 因为 “leetcode” 可以被拆分成 “leet code”。
示例 2:
输入: s = “applepenapple”, wordDict = [“apple”, “pen”]
输出: true
解释: 返回 true 因为 “applepenapple” 可以被拆分成 “apple pen apple”。
注意你可以重复使用字典中的单词。
示例 3:
输入: s = “catsandog”, wordDict = [“cats”, “dog”, “sand”, “and”, “cat”]
输出: false
笔记:采用动态规划法
class Solution:
def wordBreak(self, s: str, wordDict: List[str]) -> bool:
if not s:
return True
dp = [0]
for i in range(len(s)+1):
for j in dp:
if s[j:i] in wordDict:
dp.append(i)
break
return dp[-1] == len(s)
困难
返回该章节
单词拆分 II
给定一个非空字符串 s 和一个包含非空单词列表的字典 wordDict,在字符串中增加空格来构建一个句子,使得句子中所有的单词都在词典中。返回所有这些可能的句子。
说明:
分隔时可以重复使用字典中的单词。
你可以假设字典中没有重复的单词。
示例 1:
输入:
s = “catsanddog”
wordDict = [“cat”, “cats”, “and”, “sand”, “dog”]
输出:
[
“cats and dog”,
“cat sand dog”
]
示例 2:
输入:
s = “pineapplepenapple”
wordDict = [“apple”, “pen”, “applepen”, “pine”, “pineapple”]
输出:
[
“pine apple pen apple”,
“pineapple pen apple”,
“pine applepen apple”
]
解释: 注意你可以重复使用字典中的单词。
示例 3:
输入:
s = “catsandog”
wordDict = [“cats”, “dog”, “sand”, “and”, “cat”]
输出:
[]
笔记:解题思路:这道题不只像word break那样判断是否可以分割,而且要找到所有的分割方式,那么我们就要考虑dfs了。不过直接用dfs解题是不行的,为什么?因为决策树太大,如果全部遍历一遍,时间复杂度太高,无法通过oj。那么我们需要剪枝,如何来剪枝呢?使用word break题中的动态规划的结果,在dfs之前,先判定字符串是否可以被分割,如果不能被分割,直接跳过这一枝。实际上这道题是dp+dfs。
class Solution:
def check(self,s,wordDict):
dp = [False for i in range(len(s)+1)]
dp[0] = 1
for i in range(1,len(s)+1):
for k in range(i):
if dp[k] and s[k:i] in wordDict :
dp[i] = True
return dp[len(s)]
def dfs(self,s,wordDict,stringlist):
if self.check(s,wordDict):
if len(s) == 0:
return Solution.res.append(stringlist[1:])
for i in range(1,len(s)+1):
if s[:i] in wordDict:
self.dfs(s[i:],wordDict,stringlist + ' ' + s[:i])
def wordBreak(self, s: str, wordDict: List[str]) -> List[str]:
Solution.res= []
self.dfs(s,wordDict,'')
return Solution.res