《剑指offer》c++版本 7.重建二叉树

 如题:

输入某二叉树的前序遍历和中序遍历的结果,请重建出该二叉树。假设输入的前序遍历和
中序遍历的结果中都不含重复的数字。例如输入前序遍历序列{1,2,4,7,3,5,6,8}和中序
遍历序列{4,7,2,1,5,3,8,6},则重建二叉树并返回。

 根据前序和中序数列重建二叉树,这道题,还有一道类似题,根据后续和中序数列重建二叉树。两题解法完全一样,仅仅方向不同。这是学习二叉树的时候必做的题型,和遍历二叉树性质类似。

看题,我们知道,前序遍历得到的数列,依次是各子树的根节点,如根节点,根节点左子树,根节点右子树......,此外,中序遍历数列中,根节点的值位于中间,左右两边依次是左右子树。结合前序数列性质,我们可以这样做,先再前序数列求得根节点的值,然后,查找中序遍历,此时,中序数列中,位于根节点左边的数列即是左子树,右边的为右子树。先后求得根节点的左子树以及右子树。之后,采用递归,依次求得节点的左右子树即可。

后序遍历也是一样处理,只不过方向变反。后序遍历数列,从后往前依次是根节点,根节点右子树,根节点左子树,即左右子树求取顺序和上述题型相反。

下面是本题的c++解法:

//模板题,先计算根节点,然后分别计算左子树和右子树的根节点
class Solution {
public:
    TreeNode *constructTree(vector<int> pre,int *preStart, int preEnd, vector<int> vin, int vinStart, int vinEnd){
        int i;
        TreeNode *root;
        
        //特殊情况处理
        if (vinStart > vinEnd)    return NULL;
        root = new TreeNode(pre[*preStart]);
     
        //找到左子树和右子树的范围
        for (i = vinStart; i <= vinEnd; i++){
            if (pre[*preStart] == vin[i])
                break;
        }
        //指向下一个根节点
        *preStart = *preStart + 1;
        root->left = constructTree(pre, preStart, preEnd, vin,vinStart,i-1);
        root->right = constructTree(pre, preStart, preEnd, vin,i+1, vinEnd);
       
        return root;
    }
    
    TreeNode* reConstructBinaryTree(vector<int> pre, vector<int> vin) {
        int preStart = 0;
        if (pre.empty())    return NULL;
        return constructTree(pre, &preStart, pre.size()-1,vin,0,vin.size()-1);
    }
};

=============================================================================================

Linux应用程序、内核、驱动、后台开发交流讨论群(745510310),感兴趣的同学可以加群讨论、交流、资料查找等,前进的道路上,你不是一个人奥^_^。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值