题目描述
输入某二叉树的前序遍历和中序遍历的结果,请重建出该二叉树。假设输入的前序遍历和中序遍历的结果中都不含重复的数字。例如输入前序遍历序列{1,2,4,7,3,5,6,8}和中序遍历序列{4,7,2,1,5,3,8,6},则重建二叉树并返回。
输入输出示例
输入:[1, 2, 3, 4, 5, 6, 7], [3, 2, 4, 1, 6, 5, 7]
返回值:[1, 2, 5, 3, 4, 6, 7]
解题思路
对于已知二叉树的先序遍历和中序遍历如下:
先序:pre=[1, 2, 3, 4, 5, 6, 7]
中序:tin=[3, 2, 4, 1, 6, 5, 7]
- 先序遍历的第一个结点一定就是二叉树的根节点,root=pre[0]
- 然后找出根节点在中序遍历中所在的位置pose=tin.index(root)
- 找出根节点就可以将中序遍历中的结点划分为左子树部分节点、根节点、右子树部分节点三部分。
tinLeft=tin[:pose]
tinRight=tin[pose+1:] - 将先序遍历依据中序遍历结点在当前根节点的位置划分左子树结点、右子树结点
preLeft=pre[1:pose+1]
preRight=pre[pose+1:] - 递归实现左右子树的左右子树、根节点的划分
- 将根节点与左右子树建立连接,完成树的构建
代码示例
# -*- coding:utf-8 -*-
class TreeNode():
def __init__(self, x):
self.val = x
self.left = None
self.right = None
class Solution:
def reConstructBinaryTree(self, pre, tin):
# 考虑边界条件,判空的情况,和输入不合法的情况
# 递归终止条件
if not pre or not tin:
return None
if len(pre) != len(tin):
return None
# 找出先序遍历中的根节点,即第一个节点
root = pre[0]
# 要返回的树的根结点
rootNode = TreeNode(root)
# 找出根节点在中序遍历中的位置
pose = tin.index(root)
# 划分中序遍历的左右子树
tinLeft = tin[:pose]
tinRight = tin[pose+1:]
# 划分先去遍历的左右子树
preLeft = pre[1:pose+1]
preRight = pre[pose+1:]
# 递归进行左右子树中的找根节点、划分左右子树
leftNode = self.reConstructBinaryTree(preLeft, tinLeft)
rightNode = self.reConstructBinaryTree(preRight, tinRight)
# 递归完成后,将所有的左右子树建立连接并返回
rootNode.left = leftNode
rootNode.right = rightNode
return rootNode