【LetMeFly】105.从前序与中序遍历序列构造二叉树:分治(递归)——五彩斑斓的题解(若不是彩色的可以点击原文链接查看) 力扣题目链接:https://leetcode.cn/problems/construct-binary-tree-from-preorder-and-inorder-traversal/
给定两个整数数组 preorder
和 inorder
,其中 preorder
是二叉树的先序遍历 , inorder
是同一棵树的中序遍历 ,请构造二叉树并返回其根节点。
示例 1:
输入 : preorder = [3,9,20,15,7], inorder = [9,3,15,20,7]
输出: [3,9,20,null,null,15,7]
示例 2:
输入: preorder = [-1], inorder = [-1]
输出: [-1]
提示:
1 <= preorder.length <= 3000
inorder.length == preorder.length
-3000 <= preorder[i], inorder[i] <= 3000
preorder
和 inorder
均 无重复 元素
inorder
均出现在 preorder
preorder
保证 为二叉树的前序遍历序列
inorder
保证 为二叉树的中序遍历序列
方法一:分治(递归)
前序遍历:根 左子树 右子树
中序遍历:左子树 根 右子树
写一个函数dfs
接收前序遍历数组
和中序遍历数组
作为参数:
根据前序遍历数组
的第一个元素为根节点
建立节点
找到根节点
在中序遍历数组
中的位置
以此可得到左子树 和右子树 的长度信息
以此可确定左子树 和右子树 在两个数组中的位置
递归建立左子树 和右子树
递归的终止条件为“前序遍历数组为空”,此时返回空节点。
Tips: 可以在预处理时建立一个哈希表,以便能快速地找到根节点在中序遍历数组中的位置。
时间复杂度$O(N)$,其中$N$是节点个数
空间复杂度$O(N)$
AC代码 C++ 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 class Solution {private : unordered_map<int , vector<int >::iterator> ma; TreeNode* dfs (vector<int >::iterator preLeft, vector<int >::iterator preRight, vector<int >::iterator inLeft, vector<int >::iterator inRight) { if (preRight <= preLeft) { return nullptr ; } TreeNode* thisNode = new TreeNode (*preLeft); vector<int >::iterator loc = ma[*preLeft]; int leftLength = loc - inLeft; thisNode->left = dfs (preLeft + 1 , preLeft + leftLength + 1 , inLeft, loc); thisNode->right = dfs (preLeft + leftLength + 1 , preRight, loc + 1 , inRight); return thisNode; }public : TreeNode* buildTree (vector<int >& preorder, vector<int >& inorder) { for (vector<int >::iterator it = inorder.begin (); it != inorder.end (); it++) { ma[*it] = it; } return dfs (preorder.begin (), preorder.end (), inorder.begin (), inorder.end ()); } };
Python 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 from typing import List , Optional class TreeNode : def __init__ (self, val=0 , left=None , right=None ): self .val = val self .left = left self .right = rightclass Solution : def dfs (self, preLeft: int , preRight: int , inLeft: int , inRight: int ) -> Optional [TreeNode]: if preRight <= preLeft: return None thisNode = TreeNode(self .preorder[preLeft]) loc = self .ma[self .preorder[preLeft]] leftLength = loc - inLeft thisNode.left = self .dfs(preLeft + 1 , preLeft + leftLength + 1 , inLeft, loc - 1 ) thisNode.right = self .dfs(preLeft + leftLength + 1 , preRight, loc + 1 , inRight) return thisNode def buildTree (self, preorder: List [int ], inorder: List [int ] ) -> TreeNode: self .preorder = preorder self .inorder = inorder self .ma = dict () for i in range (len (inorder)): self .ma[inorder[i]] = i return self .dfs(0 , len (preorder), 0 , len (inorder))
同步发文于CSDN,原创不易,转载经作者同意后请附上原文链接 哦~ Tisfy:https://letmefly.blog.csdn.net/article/details/136186356