Leetcode-python-二叉樹的遍歷

題目來自Leetcoode,引用了一些題解和評論裏面的代碼翻譯成了Python·。如有侵權,請聯繫。

二叉樹的前序遍歷 ->144. 二叉樹的前序遍歷

遞歸寫法:

# Definition for a binary tree node.
# class TreeNode:
#     def __init__(self, x):
#         self.val = x
#         self.left = None
#         self.right = None
class Solution:
    def preorderTraversal(self, root: TreeNode) -> List[int]:
        L = []
        if not root:return []
        
        def t(node):
            L.append(node.val) 
            if node.left:
                t(node.left)
            if node.right :
                t(node.right)
        t(root)
        return L

非遞歸的寫法:

class Solution:
    def preorderTraversal(self, root: TreeNode) -> List[int]:
        if not root:return []
        stack = [root]
        L = []
        while(stack):
            Q = stack.pop(-1)
            L.append(Q.val)
            if Q.right:    ######注意是先right後left
                stack.append(Q.right)
            if Q.left:
                stack.append(Q.left)
        return L

        # 另外一種
        if not root:return []
        s = []
        ans = []
        node = root
        while(node or s):
            while(node):
                ans.append(node.val) # 存根節點
                s.append(node)       # 爲了判斷右子樹
                node = node.left     # 直到最左子樹
            node = s[-1].right       # 最左子樹的右子樹
            s.pop()
        return ans
    

注意利用棧去存節點的時候,先right後left。因爲棧是先進後出的,如果[left,right] => pop() => [right,left]所以要先存right。

二叉樹的中序遍歷 ->94. 二叉樹的中序遍歷

遞歸版本

class Solution:
    def inorderTraversal(self, root: TreeNode) -> List[int]:
        if not root:return []
        L = []
        def t(node):
            if node.left:
                t(node.left)
            L.append(node.val)
            if node.right:
                t(node.right) 
        t(root)
        return L

非遞歸版本(迭代) 代碼來自此處@weih1121

# 中序遍歷 先遍歷左子樹->根節點->右子樹
# 如果是遞歸做法則遞歸遍歷左子樹,訪問根節點,遞歸遍歷右子樹
# 非遞歸過程即:先訪問..最左子樹..結點,再訪問其父節點,再訪問其兄弟
# while循環條件 中序遍歷需先判斷當前結點是否存在,若存在則將該節點放入棧中,再將當前結點設置爲結點的左孩子,
# 若不存在則取棧頂元素[最左節點]爲cur,在訪問cur的右節點。
# 當且僅當棧空cur也爲空,循環結束。
class Solution:
    def inorderTraversal(self, root: TreeNode) -> List[int]:        
        if not root:return []
        s = []
        v = []
        node = root
        while(node or s):
            if node : 
                s.append(node)
                node = node.left
            else:
                node = s.pop(-1) # 最後一個
                v.append(node.val)
                node  = node.right
        return v 

二叉樹的後序遍歷 ->145. 二叉樹的後序遍歷

遞歸版本

class Solution:
    def postorderTraversal(self, root: TreeNode) -> List[int]:
        if not root:return []
        L = []
        def t(node):
            if node.left:
                t(node.left)
            if node.right:
                t(node.right) 
            L.append(node.val)
        t(root)
        return L

非遞歸版本

(1)輸出層次遍歷的逆

class Solution(object):
    def postorderTraversal(self, root):
        # 層次遍歷從左到右,從上到下 -> 隊列
        # 深度遍歷從左到右,從下到上 -> 棧
        # 棧:根->左->右
        # output:根->右->左 層次不會變
        # output[::-1]:左->右->根

        if root is None:
            return []

        stack, output = [root, ], []
        while stack:
            print([node.val for node in stack])
            root = stack.pop()

            output.append(root.val)
            if root.left is not None:
                stack.append(root.left)
            if root.right is not None:
                stack.append(root.right)          
        return output[::-1]

(2)利用pre判斷右節點是否被輸出,從左到右的去遍歷。來自此處

        if not root: return []
        s,v = [],[]
        cur = root
        pre = None

        while(cur or s):
            while(cur):
                s.append(cur)
                cur=cur.left ##遍歷左子樹
            cur = s[-1]
            if cur.right == None or cur.right == pre: #判斷是否該輸出結點
                v.append(cur.val)
                s.pop()
                pre = cur
                cur = None
            else:
                cur=cur.right
        return v

二叉樹的層次遍歷

107. 二叉樹的層次遍歷 II

199. 二叉樹的右視圖

if not root:return []
q = [root]
L = []
while(q):
    node=q.pop(0) #隊列,先進先出
    L.append(node.val)
    if node.left:
        q.append(node.left)
    if node.right:
        q.append(node.right)
return L

二叉樹的深度 -> 面試題55 - I. 二叉樹的深度 

104. 二叉樹的最大深度

遞歸

class Solution:
    def maxDepth(self, root: TreeNode) -> int:
        
        def t(root): O(N) O(N)
            if not root:
                return 0
            left = t(root.left)+1
            right = t(root.right)+1
            return left if left>right else right
        depth = t(root)
        return depth

非遞歸(層次遍歷的層數)

class Solution:
    def maxDepth(self, root: TreeNode) -> int:        
        # 層次遍歷的層數 O(N) O(N)
        if not root:return 0
        q = [root]
        ans = 0
        while(q):
            ans +=1
            size = len(q)
            for i in range(0,size):
                node = q.pop(0)
                if node.left:
                    q.append(node.left)
                if node.right:
                    q.append(node.right) 
        return ans

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章