本文介绍 LeetCode 题集中,有关二叉树遍历的问题。
105. Construct Binary Tree from Preorder and Inorder Traversal(从前序与中序遍历序列构造二叉树)
问题描述
思路与代码
由于前序遍历的左端为根节点,可从中序遍历中找到根节点的位置,则其左侧为左子树,右侧为右子树,递归还原出原树即可。
代码如下:
# 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 buildTree(self, preorder: List[int], inorder: List[int]) -> TreeNode:
# edge cases
if not preorder or not inorder or len(preorder) != len(inorder):
return None
# 哈希表(字典)降低时间复杂度
dic_index = {inorder[i]: i for i in range(len(inorder))}
def rec(p_start: int, p_end: int, i_start: int, i_end: int):
# 由于参数中的起止点为闭区间,故终止条件为 >
# 此处使用 p_start > p_end 亦可
if i_start > i_end:
return None
root = TreeNode(val=preorder[p_start])
pos = dic_index[preorder[p_start]]
root.left = rec(p_start=p_start + 1, p_end=p_start + (pos - i_start), i_start=i_start, i_end=pos - 1)
root.right = rec(p_start=p_end - (i_end - pos) + 1, p_end=p_end, i_start=pos + 1, i_end=i_end)
return root
return rec(p_start=0, p_end=len(preorder) - 1, i_start=0, i_end=len(inorder) - 1)
代码中有几处需要注意:
- 注意递归函数的参数,即起止点的区间为闭区间,对应地,终止条件为 ‘>’ 比较
- 在中序遍历中查询根节点的位置,可以通过哈希表来降低时间复杂度
运行效果:
106. Construct Binary Tree from Inorder and Postorder Traversal(从中序与后序遍历序列构造二叉树)
问题描述
思路与代码
本题的思路与前一题相似,区别在于后序遍历的右端为根节点,只要修改递归函数中左右节点的位置参数即可。
代码如下:
# 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 buildTree(self, inorder: List[int], postorder: List[int]) -> TreeNode:
if not inorder or not postorder or len(inorder) != len(postorder):
return None
dic_index = {inorder[i]: i for i in range(len(inorder))}
def rec(p_start: int, p_end: int, i_start: int, i_end: int):
# 此处使用 p_start > p_end 亦可
if i_start > i_end:
return None
root = TreeNode(val=postorder[p_end])
pos = dic_index[postorder[p_end]]
root.left = rec(p_start=p_start, p_end=p_start + (pos - i_start) - 1, i_start=i_start, i_end=pos - 1)
root.right = rec(p_start=p_start + (pos - i_start), p_end=p_end - 1, i_start=pos + 1, i_end=i_end)
return root
return rec(p_start=0, p_end=len(postorder) - 1, i_start=0, i_end=len(inorder) - 1)
运行效果: