【二叉樹】LeetCode 102. 二叉樹的層序遍歷【中等】

給你二叉樹的根節點 root ,返回其節點值的 層序遍歷 。 (即逐層地,從左到右訪問所有節點)。

示例 1:

 

 

輸入:root = [3,9,20,null,null,15,7]
輸出:[[3],[9,20],[15,7]]
示例 2:

輸入:root = [1]
輸出:[[1]]
示例 3:

輸入:root = []
輸出:[]
 

提示:

樹中節點數目在範圍 [0, 2000] 內
-1000 <= Node.val <= 1000

分析

方法一:迭代實現

廣度優先遍歷是按照層層推進的方式,遍歷每一層的節點。題目要求的是返回每一層的節點值,所以這道題非常適合用廣度優先來做。

廣度優先需要用隊列作爲輔助結構,我們先將根結點放到隊列中,然後不斷遍歷隊列。

首先拿出根節點,如果左子樹/右子樹不爲空,就將他們也都放入隊列中。第一遍處理完後,根節點已經從隊列中拿走了,而根節點的兩個孩子已放入隊列中,現在隊列中就有了兩個節點2和5。

第二層處理會將2和5這兩個節點從隊列中拿走,然後再將2和5的子節點放入隊列中,現在隊列中就有三個節點3,4,6。

我們把每一層遍歷到的節點都放入到一個結果集中,最後返回這個結果就可以了。

時間複雜度:O(n) 

空間複雜度:O(n)

# Definition for a binary tree node.
# class TreeNode:
#     def __init__(self, val=0, left=None, right=None):
#         self.val = val
#         self.left = left
#         self.right = right
class Solution:
    def levelOrder(self, root: TreeNode) -> List[List[int]]:
        if not root:
            return []
        
        res = []
        queue = [root]
        while queue:
            # 獲取當前隊列的長度,這個長度相當於當前這一層的節點個數
            size = len(queue)
            tmp = [] # 定義臨時列表,用於

            # 將隊列中的元素都拿出來(也就是獲取這一層的節點),放到臨時list中
            # 如果節點的左子樹/右子樹不爲空,也放入隊列中
            for _ in range(size):
                r = queue.pop(0)
                tmp.append(r.val)
                if r.left:
                    queue.append(r.left)
                if r.right:
                    queue.append(r.right)
            # 將臨時列表tmp加入最終的返回結果中
            res.append(tmp)
        
        return res

方法二:遞歸實現

用廣度優先處理是很直觀的,可以想象成是一把刀橫着切割了樹的每一層。

但是深度優先遍歷就不那麼直觀了。我們開下腦洞,把二叉樹的樣子調整一下,擺成一個田字形的樣子。田字形的每一層就對應一個list。

 

按照深度優先的處理順序,會先訪問節點1,再訪問節點2,接着是節點3。

之後是第二列的節點4,5。最後是第三列的節點6。

每次遞歸的時候都需要帶一個index(表示當前的層數),也就對應那個田字格子中的第幾行,如果當前行對應的list不存在,就加入一個空list進去

時間複雜度:O(n)

空間複雜度:O(h), h爲樹高度。

class Solution(object):
    def levelOrder(self, root):
        """
        :type root: TreeNode
        :rtype: List[List[int]]
        """
        if not root:
            return []
        res = []
        def dfs(index,r):
            # 假設res是[ [1],[2,3] ], index是3,就再插入一個空list放到res中
            if len(res)<index:
                res.append([])
            #  將當前節點的值加入到res中,index代表當前層,假設index是3,節點值是99
            # res是[ [1],[2,3] [4] ],加入後res就變爲 [ [1],[2,3] [4,99] ]
            res[index-1].append(r.val)
            # 遞歸的處理左子樹,右子樹,同時將層數index+1
            if r.left:
                dfs(index+1,r.left)
            if r.right:
                dfs(index+1,r.right)
        dfs(1,root)
        return res

 

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