1. 程式人生 > 其它 >LeetCode-144:二叉樹的前序遍歷

LeetCode-144:二叉樹的前序遍歷

技術標籤:letcode刷題筆記及程式碼實現

題目描述:

給你二叉樹的根節點root,返回它節點值的前序遍歷。

輸入:root = [1,null,2,3]
輸出:[1,2,3]

思路分析:

遞迴或是迭代實現。

遞迴:

首先我們需要了解什麼是二叉樹的前序遍歷:按照訪問根節點——左子樹——右子樹的方式遍歷這棵樹,而在訪問左子樹或者右子樹的時候,我們按照同樣的方式遍歷,直到遍歷完整棵樹。因此整個遍歷過程天然具有遞迴的性質,我們可以直接用遞迴函式來模擬這一過程。

定義 preorder(root) 表示當前遍歷到 root 節點的答案。按照定義,我們只要首先將 root 節點的值加入答案,然後遞迴呼叫 preorder(root.left) 來遍歷 root 節點的左子樹,最後遞迴呼叫 preorder(root.right) 來遍歷 root 節點的右子樹即可,遞迴終止的條件為碰到空節點。

class Solution {
    public List<Integer> preorderTraversal(TreeNode root) {
        List<Integer> res = new ArrayList<Integer>();
        preorder(root, res);
        return res;
    }

    public void preorder(TreeNode root, List<Integer> res) {
        if (root == null) {
            return;
        }
        res.add(root.val);
        preorder(root.left, res);
        preorder(root.right, res);
    }
}

時間複雜度:O(n)O(n),其中 nn 是二叉樹的節點數。每一個節點恰好被遍歷一次。

空間複雜度:O(n)O(n),為遞迴過程中棧的開銷,平均情況下為 O(\log n)O(logn),最壞情況下樹呈現鏈狀,為 O(n)O(n)。

迭代:

本質上是在模擬遞迴,因為在遞迴的過程中使用了系統棧,所以在迭代的解法中常用Stack來模擬系統棧。

class Solution {
    public List<Integer> preorderTraversal(TreeNode root) {
        List<Integer> res = new ArrayList<Integer>();
        if (root == null) {
            return res;
        }

        Deque<TreeNode> stack = new LinkedList<TreeNode>();
        TreeNode node = root;
        while (!stack.isEmpty() || node != null) {
            while (node != null) {
                res.add(node.val);
                stack.push(node);
                node = node.left;
            }
            node = stack.pop();
            node = node.right;
        }
        return res;
    }
}

時間複雜度:O(n)O(n),其中 nn 是二叉樹的節點數。每一個節點恰好被遍歷一次。

空間複雜度:O(n)O(n),為迭代過程中顯式棧的開銷,平均情況下為 O(\log n)O(logn),最壞情況下樹呈現鏈狀,為 O(n)O(n)。