106-LeetCode 从中序与后序遍历序列构造二叉树

文章目录

    • 题目
    • 法一:递归


题目

从中序与后序遍历序列构造二叉树。根据一棵树的中序遍历与后序遍历构造二叉树。

注意:
你可以假设树中没有重复的元素。例如,给出
中序遍历 inorder = [9,3,15,20,7]
后序遍历 postorder = [9,15,7,20,3]

返回如下的二叉树:
3
/ \
9 20
    / \
  15 7




法一:递归

思路:
中序遍历: 左
后序遍历: 左 右

  • 根据 后序序列 得到 ------ 根节点的值
  • 根据 中序序列 + 根节点的值 得到-------中序序列中 根节点的下标
  • 根据 中序序列 + 根节点的下标 得到-----中序序列中 左子树的长度

代码如下:

#include 
#include 
#include 
#include 
#include 
#include 

using namespace std;

struct TreeNode
{
    int data;
    TreeNode * left;
    TreeNode * right;
    TreeNode(int value)
    {
        data = value;
        left = NULL;
        right = NULL;
    }
};

map<int , int> index;       // 中序序列  数据----下标
TreeNode * myTreeBuild(vector<int> &  inOrder , vector<int> & backOrder , int in_left , int in_right , int back_left ,  int back_right)
{
    if(back_left > back_right)
    {
        return NULL;
    }

    // 得到根节点的值
    int root_value = backOrder[back_right];

    // 得到中序序列 中 根节点的下标
    int in_root = index[root_value];

    // 得到左子树的长度
    int left_len = in_root - in_left;
 
    // 中序遍历下标       左                      根                          右
    // 中序遍历         in_left                in_root                    in_right
    // 后序遍历下标       左                      右                          根                          
    // 后序遍历         back_left          back_left + left_len           back_right

    TreeNode * root = new TreeNode(root_value);
    root->left = myTreeBuild(inOrder , backOrder , in_left , in_root-1 , back_left , back_left + left_len - 1);
    root->right = myTreeBuild(inOrder , backOrder , in_root + 1 , in_right , back_left + left_len , back_right - 1);

    return root;
}


TreeNode * BuildTree(vector<int> & inOrder , vector<int> & backOrder)
{
    if(inOrder.empty() || backOrder.empty())
    {
        return NULL;
    }

    int size = inOrder.size();

    for(int i = 0; i < size ; i++)
    {
        index[inOrder[i]] = i;
    }

    return myTreeBuild(inOrder , backOrder , 0 , size - 1 , 0 , size - 1);
}

// 层序输出构建的二叉树
void PrintFromTopToBottom(TreeNode * root)
{
    if(root == NULL)
    {
        return;
    }

    list<TreeNode *> l;
    l.push_back(root);

    while(!l.empty())
    {
        TreeNode * temp = l.front();
        cout << temp->data << " ";
        l.pop_front();

        if(temp->left)
        {
            l.push_back(temp->left);
        }
        if(temp->right)
        {
            l.push_back(temp->right);
        }
    }
    cout << endl;
}


int main()
{
    vector<int> inOrder;
    inOrder.push_back(9);
    inOrder.push_back(4);
    inOrder.push_back(12);
    inOrder.push_back(8);
    inOrder.push_back(1);
    inOrder.push_back(2);
    inOrder.push_back(5);

    vector<int> backOrder;
    backOrder.push_back(9);
    backOrder.push_back(12);
    backOrder.push_back(4);
    backOrder.push_back(1);
    backOrder.push_back(5);
    backOrder.push_back(2);
    backOrder.push_back(8);

    TreeNode * root = BuildTree(inOrder , backOrder);
    PrintFromTopToBottom(root);

    return 0;
}

按照层序遍历输出我们构建的二叉树:

8 4 2 9 12 1 5 

你可能感兴趣的:(LeetCode,LeetCode,106,中序和后序序列构建二叉树,二叉树的构建)