概述
给出两个数组,分别代表二叉树的后序和内序遍历。我们的目标是用它们来构建一棵二叉树。
例子。
考虑下面这棵树

该树的后序遍历将是
[1,2,4,3,5,6]
该树的无序遍历将是
[4,2,1,5,3,6]
我们将给出后序和内序数组,我们必须从内序和后序中再次构建树。以下是我们的策略
-
我们将使用三个索引,即数组的开始、数组的结束和当前索引
-
后序中的最后一个索引将是根。
-
我们将在一个内序数组中找到其值与后序数组中最后一个索引的值相匹配的索引。让我们把这个索引称为rootIndex
-
内序数组中rootIndex左边的所有值都将在左子树中。
-
顺序数组中rootIndex右边的所有值将在右子树中。
-
然后我们可以用同样的策略对右子树进行递归,然后再对左子树进行递归。
例如
-
后序遍历中的最后一个索引是根,其值为1
-
值1在后序遍历的第二个索引处。因此rootIndex是2
-
在后序遍历中rootIndex的左边是**[4,2]**,它是左边子树的一部分。
-
rootIndex在顺序遍历中的右边是**[5,3,6]**,是右子树的一部分。
-
我们可以对右子树进行递归,然后再对左子树进行递归。
程序
package main
import (
"fmt"
)
type TreeNode struct {
Val int
Left *TreeNode
Right *TreeNode
}
func buildTree(inorder []int, postorder []int) *TreeNode {
lenTree := len(inorder)
index := lenTree - 1
return buildTreeUtil(inorder, postorder, &index, 0, lenTree-1)
}
func buildTreeUtil(inorder []int, postorder []int, index *int, low, high int) *TreeNode {
if low > high {
return nil
}
if low == high {
currentIndexValue := postorder[*index]
(*index)--
return &TreeNode{Val: currentIndexValue}
}
currentIndexValue := postorder[*index]
(*index)--
root := &TreeNode{Val: currentIndexValue}
mid := 0
for i := low; i <= high; i++ {
if inorder[i] == currentIndexValue {
mid = i
}
}
root.Right = buildTreeUtil(inorder, postorder, index, mid+1, high)
root.Left = buildTreeUtil(inorder, postorder, index, low, mid-1)
return root
}
func main() {
inorder := []int{4, 2, 1, 5, 3, 6}
postorder := []int{4, 2, 5, 6, 3, 1}
root := buildTree(inorder, postorder)
fmt.Printf("root: %d\n", root.Val)
fmt.Printf("root.Left: %d\n", root.Left.Val)
fmt.Printf("root.Left.Left: %d\n", root.Left.Left.Val)
fmt.Printf("root.Right: %d\n", root.Right.Val)
fmt.Printf("root.Right.Left: %d\n", root.Right.Left.Val)
fmt.Printf("root.Right.Right: %d\n", root.Right.Right.Val)
}
输出
root: 1
root.Left: 2
root.Left.Left: 4
root.Right: 3
root.Right.Left: 5
root.Right.Right: 6