Leetcode刷题(31)二叉树专题(31)二叉树专题:树的后序遍历(递归和迭代)

题目

145. 二叉树的后序遍历

在这里插入图片描述

难度:困难
题目分析:如果采用递归的方法,那难度其实等于0。

对于后序遍历来说,最难的其实是迭代的方法。因为后序遍历的顺序是 左-右-根,这意味着,找到最左的叶子之后,还要再往右边可能的叶子找,最后才能输出根节点位置的值。

2. 解法一:递归

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

class Solution:
    def postorderTraversal(self, root: TreeNode) -> List[int]:
        # 递归
        res = []
        def dfs(root):
            if not root:
                return
            
            dfs(root.left)
            dfs(root.right)
            res.append(root.val)
            
        dfs(root)
        return res

2.1 运行结果

在这里插入图片描述
在这里插入图片描述

3.解法三:第二种递归方法

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

class Solution:
    def postorderTraversal(self, root: TreeNode) -> List[int]:
    	# 第二种递归的方法
        if not root:
            return []
        res = []

        res += self.postorderTraversal(root.left)
        res += self.postorderTraversal(root.right)

        res.append(root.val)

        return res

3.1 运行结果:

在这里插入图片描述
在这里插入图片描述

3.2 分析:

之前根据别人的模板,完全忽略了可以不用额外定义函数,而直接进行递归。

这里的速度和内存占用,跟之前的方法差别不大。

在代码的组织上,具备了递归程序的一切优点。建立空列表,然后把左子树后序遍历结果附上;再附上右子树后序遍历的结果;最后附上根节点的值

4. 解法三:迭代的方法

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

class Solution:
    def postorderTraversal(self, root: TreeNode) -> List[int]:
    	# 运用迭代的方法求解
        res, stack = [], []

        while stack or root:
            while root:
                stack.append(root)
                root = root.left if root.left else root.right

            # 跳出循环后,说明已经走到最下面,可以读取
            node = stack.pop()
            res.append(node.val)

            if stack and node == stack[-1].left:
                root = stack[-1].right
            else:
                root = None

        return res

4.1 运行结果:

在这里插入图片描述
在这里插入图片描述

4.2 分析:

还好,通过回忆还能正确写出迭代的算法。

这里的关键是第二个while循环,不仅要一直沿着左子树前进,当左子树为空时,就要切换成右子树,然后继续往左前进。

跳出 while 循环的时候,一定是最左侧的叶节点了。于是,这个点的数据可以读取。

接下来是难点。此时栈顶存储的元素是该叶节点的父节点,我们要判断已经记录的点是该父节点的左子树还是右子树。

如果是左子树,意味父节点还不能弹出,root 的值要设为父节点的右子树,继续进行探索。

如果是右子树,则说明父节点的值可以读取。此时,设root为None, 根据程序逻辑,就会自动弹出父节点进行读取。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值