1. 程式人生 > >DFS+回溯專題12 - leetcode95. Unique Binary Search Trees II/394. Decode String - Mark

DFS+回溯專題12 - leetcode95. Unique Binary Search Trees II/394. Decode String - Mark

95. Unique Binary Search Trees II

題目描述

給定整數n,產生儲存1…n的結構上唯一的二叉搜尋樹。

例子

Input: 3
Output:
[
[1,null,3,2],
[3,2,null,1],
[3,1,null,null,2],
[2,1,3],
[1,null,2,null,3]
]

思想
注意輸出的是合法根節點的列表。
DFS輸入是所儲存數的範圍,遍歷該範圍選定root,然後遞迴求得left和right。

(改進) 字典儲存曾經處理過的範圍

解法

# Definition for a binary tree node.
# class TreeNode(object): # def __init__(self, x): # self.val = x # self.left = None # self.right = None class Solution(object): def generateTrees(self, n): """ :type n: int :rtype: List[TreeNode] """ if n <= 0: return
[] return self.dfs(1, n) def dfs(self, start, end): if start > end: return [None] res = [] for root in range(start, end+1): for left in self.dfs(start, root-1): for right in self.dfs(root+1, end): node =
TreeNode(root) node.left = left node.right = right res.append(node) return res

改進:字典

# Definition for a binary tree node.
# class TreeNode(object):
#     def __init__(self, x):
#         self.val = x
#         self.left = None
#         self.right = None

class Solution(object):
    def generateTrees(self, n):
        """
        :type n: int
        :rtype: List[TreeNode]
        """
        if n <= 0:
            return []
        self.cache = {}
        return self.dfs(1, n)
    
    def dfs(self, start, end):
        if start > end:
            return [None]
        if (start, end) not in self.cache:
            res = []
            for root in range(start, end+1):
                for left in self.dfs(start, root-1):
                    for right in self.dfs(root+1, end):
                        node = TreeNode(root)
                        node.left = left
                        node.right = right
                        res.append(node)
            self.cache[(start, end)] = res
        return self.cache[(start, end)]

394. Decode String

題目描述

給定一個已經編碼的字串,返回解碼後的字串。
編碼規則:k[encoded_string]表示字串encoded_string重複k次。

保證k是正整數;假設輸入合法;沒有額外的空格、方括號格式正確。假設原始資料不包含數字,只有重複次數是數字。

例子

s = “3[a]2[bc]”, return “aaabcbc”.
s = “3[a2[c]]”, return “accaccacc”.
s = “2[abc]3[cd]ef”, return “abcabccdcdcdef”.

思想
一個比較棘手的例子是3[a2[c]]。可以看出只有遇到字元 ‘]’ 時,才考慮解碼操作。
(法1 - DFS)
DFS主體:遍歷字串,截取出數字部分,和數字後面的方括號部分(該部分DFS - decodeString).
截止條件:方括號部分只包含字元時,直接返回該字元;否則接著按遞迴遍歷。

(法2 - 棧)
需儲存數字和字串。遇到 ']‘時才進行彈出和計算處理;處理後記著繼續壓棧,例如該情況’3[a2[c]]’。

解法1
DFS

class Solution(object):
    def decodeString(self, s):
        """
        :type s: str
        :rtype: str
        """
        res = ''
        i = 0
        while i < len(s):
            if not s[i].isdigit() and s[i] != '[' and s[i] != ']':
                res += s[i]
                i += 1
            else:
                # Get repeat-times
                j = i
                while '0' <= s[j] <= '9':
                    j += 1
                repeat = int(s[i:j])
                # Get the strings between square brackets
                cnt = 0
                i = j + 1
                while i < len(s) and cnt >= 0:
                    if s[i] == '[':
                        cnt += 1
                    elif s[i] == ']':
                        cnt -= 1
                    i += 1
                res += repeat * self.decodeString(s[j+1:i-1])
        return res

解法2

class Solution(object):
    def decodeString(self, s):
        """
        :type s: str
        :rtype: str
        """
        num = 0
        stack = [['', '']]
        for c in s:
            if '0' <= c <= '9':
                num = num * 10 + ord(c) - 48
            elif c == '[':
                stack.append([num, ''])
                num = 0
            elif c == ']':
                k, ss = stack.pop()
                stack[-1][1] += k * ss
            else:
                stack[-1][1] += c
        return stack[0][1]