定个小目标之刷LeetCode热题(37)

105. 从前序与中序遍历序列构造二叉树

给定两个整数数组 preorderinorder ,其中 preorder 是二叉树的先序遍历inorder 是同一棵树的中序遍历,请构造二叉树并返回其根节点。

今天看这道题目,首先要先搞懂先序遍历和中序遍历的概念,我记得口诀是先序遍历根左右,中序遍历左根右,按照这个规则遍历二叉树,然后把其存储在数组中,现在是反过来,给出已知先序遍历和中序遍历的两个数组,我们需要把这个二叉树构造出来,具体解题思路看代码

class Solution {

    Map<Integer, Integer> indexMap;

    public TreeNode recursionBuildTree(int[] preorder, int[] inorder, int preorder_left, int preorder_right,
            int inorder_left, int inorder_right) {
        // 左边界必须小于等于右边界,否则返回null
        if (preorder_left > preorder_right) {
            return null;
        }
        // 因为前序遍历是根左右,所以第一个元素就是根节点,获取其value
        int preorder_root = preorder_left;
        // 有了root的值,那么就可以知道其在中序遍历数组的下标
        int inorder_root = indexMap.get(preorder[preorder_root]);
        // 中序遍历是左根右,即根节点的左边是左子树的元素,右边是右子树的元素,所以根据根节点的下标可以计算出左子树元素大小
        int inorder_left_size = inorder_root - inorder_left;
        // 先把根节点构造出来
        TreeNode root = new TreeNode(preorder[preorder_root]);
        // 利用递归将根节点的左子树构造出来,这里传递的索引都是左子树的区间
        root.left = recursionBuildTree(preorder, inorder, preorder_left + 1, preorder_left + inorder_left_size,
                inorder_left, inorder_root - 1);
        // 利用递归将根节点的右子数构造出来,这里传递的索引都是右子树的区间
        root.right = recursionBuildTree(preorder, inorder, preorder_left + inorder_left_size + 1, preorder_right,
                inorder_root + 1, inorder_right);
        return root;
    }

    public TreeNode buildTree(int[] preorder, int[] inorder) {
        int n = inorder.length;
        // 因为是数组结构,要想快速获取某个value的下标则不方便,于是将inorder这个数组元素存储到Map中,便于获取各节点下标
        indexMap = new HashMap<Integer, Integer>();
        for (int i = 0; i < n; i++) {
            indexMap.put(inorder[i], i);
        }
        return recursionBuildTree(preorder, inorder, 0, n - 1, 0, n - 1);
    }
}

题目链接:题单 - 力扣(LeetCode)全球极客挚爱的技术成长平台

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值