推理二叉树
难度:
标签:
题目描述
English description is not available for the problem. Please switch to Chinese.
代码结果
运行时间: 224 ms, 内存: 19.1 MB
/*
* 思路:
* 1. 前序遍历的第一个元素是根节点。
* 2. 在中序遍历中找到根节点的位置,其左边是左子树,右边是右子树。
* 3. 递归构建左子树和右子树。
* 4. 使用 Java Stream API 简化代码。
*/
import java.util.HashMap;
import java.util.Map;
import java.util.stream.IntStream;
class TreeNode {
int val;
TreeNode left;
TreeNode right;
TreeNode(int x) { val = x; }
}
public class Solution {
private Map<Integer, Integer> inorderIndexMap;
private int preorderIndex;
public TreeNode buildTree(int[] preorder, int[] inorder) {
preorderIndex = 0;
inorderIndexMap = IntStream.range(0, inorder.length).boxed().collect(Collectors.toMap(i -> inorder[i], i -> i));
return helper(preorder, 0, inorder.length - 1);
}
private TreeNode helper(int[] preorder, int inorderStart, int inorderEnd) {
if (inorderStart > inorderEnd) {
return null;
}
int rootVal = preorder[preorderIndex++];
TreeNode root = new TreeNode(rootVal);
int inorderIndex = inorderIndexMap.get(rootVal);
root.left = helper(preorder, inorderStart, inorderIndex - 1);
root.right = helper(preorder, inorderIndex + 1, inorderEnd);
return root;
}
}
解释
方法:
此题解采用的是递归的方式来构建二叉树。首先根据前序遍历的第一个元素确定树的根节点,然后在中序遍历中找到该根节点,从而区分出左子树和右子树的中序遍历。利用中序遍历中左、右子树的长度,可以相应地从前序遍历中划分出左右子树的前序遍历序列。这样,递归地对左右子树进行相同的构建过程,直到所有的子树都被正确构建。
时间复杂度:
O(n^2)
空间复杂度:
O(n)
代码细节讲解
🦆
为什么在题解中在中序遍历数组中查找根节点的索引时不直接使用哈希表,而是选择了线性搜索?
▷🦆
在构建左右子树的递归调用中,为何左子树的递归结束条件是`pstart+left_length`而右子树的开始条件是`pstart+left_length+1`?这里的+1是如何确定的?
▷🦆
题解中的递归函数`build`在何种情况下会返回`None`?这是否意味着在某些情况下子树可能不存在?
▷🦆
在这种树的构建方法中,是否有可能通过优化递归过程来进一步提高算法性能?例如通过尾递归优化等技术?
▷