Skip to content

二叉树的前序遍历

约 532 字大约 2 分钟

动态规划归并回溯

2025-02-27

144. 二叉树的前序遍历

给你二叉树的根节点 root ,返回它节点值的 前序 遍历。

示例 1:

img.png

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

示例 2:

输入:root = []
输出:[]

示例 3:

输入:root = [1]
输出:[1]

提示:

  • 树中节点数目在范围 [0, 100]
  • -100 <= Node.val <= 100

进阶:递归算法很简单,你可以通过迭代算法完成吗?

动态规划,后序归并

每层递归都新建一个res,用于存储以本节点为根节点的二叉树的前序遍历的结果。

先把根节点放入链表,再把左右子树的前序遍历结果加入链表。没有承上,只有启下。

递归的返回值是以本节点为根节点的树的前序遍历的结果。结束条件是遇到null

动态规划有返回值,会利用子递归的返回值来构建父递归的返回值

class Solution {
    // 定义:输入一个节点,返回以该节点为根的二叉树的前序遍历结果
    public List<Integer> preorderTraversal(TreeNode root) {
        // 每次都会定义一个res。重点。
        List<Integer> res = new LinkedList<>();
        // 特殊条件和前进结束条件
        if (root == null) {
            return res;
        }
        
        // 前序遍历结果特点:第一个是根节点的值,接着是左子树,最后是右子树
        res.add(root.val);
        res.addAll(preorderTraversal(root.left));
        res.addAll(preorderTraversal(root.right));
        return res;
    }
}

时间复杂度O(n),即遍历整棵二叉树。空间复杂度O(h),h是树的高度。

回溯,无返回值无信息参数的DFS+全局变量。

对每层递归,先添加节点,再进入左右子递归。

回溯没有返回值,直接在递归内部操作完了。和动态规划的区别不大

class Solution {
    List<Integer> res = new LinkedList<>();

    // 返回前序遍历结果
    public List<Integer> preorderTraversal(TreeNode root) {
        traverse(root);
        return res;
    }

    // 二叉树遍历函数
    void traverse(TreeNode root) {
        if (root == null) {
            return;
        }
        // 前序遍历位置
        res.add(root.val);
        traverse(root.left);
        traverse(root.right);
    }
}