l_in.emplace_back(inorder[i]);
i++;
}
i++; //跳过根节点
//右子树的中序遍历
while (i <= in_len - 1) {
r_in.emplace_back(inorder[i]);
i++;
}
int j = 0;
vector<int> l_post;
vector<int> r_post;
int post_len = postorder.size();
// 左子树的后序遍历
int l_len = l_in.size();
int k = 0;
while (k < l_len)
{
l_post.emplace_back(postorder[j]);
j++;
k++;
}
//右子树的后序遍历
while (j < post_len-1)
{
r_post.emplace_back(postorder[j]);
j++;
}
//递归生成左右子树
r->left = buildTree(l_in,l_post);
r->right = buildTree(r_in,r_post);
return r;
}
记得边界条件,空树。
优化就是使用了emplace\_back、size()函数写在for循环外面、加了一个为size为1时的停止条件,少递归一层。
### 结果
![](https://img-blog.csdnimg.cn/20200925105931276.PNG)
递归过程
## 优秀题解
<https://leetcode-cn.com/problems/construct-binary-tree-from-inorder-and-postorder-traversal/solution/di-gui-jian-shu-jiang-jie-de-hen-xiang-xi-by-lllll/>
## 提升笔记
1. leetcode中可以再写函数
2. unordermap做哈希表
## 全部代码
/*
Project: 106. 从中序与后序遍历序列构造二叉树
Date: 2020 / 09 / 25
Author: Frank Yu
- /
/** - Definition for a binary tree node.
- struct TreeNode {
-
int val;
-
TreeNode *left;
-
TreeNode *right;
-
TreeNode(int x) : val(x), left(NULL), right(NULL) {}
- };
*/
#include
#include
#include<unordered_map>
using namespace std;
struct TreeNode {
int val;
TreeNode left;
TreeNode right;
TreeNode(int x) : val(x), left(NULL), right(NULL) {}
};
class Solution {
unordered_map<int, int> index;
public:
// 优化
TreeNode myBuildTree(vector& postorder, vector& inorder, int postorder_left, int postorder_right, int inorder_left, int inorder_right) {
// 空树
if (postorder_left > postorder_right) return NULL;
// 后序中序下标
int postorder_root = postorder_right;
int inorder_root = index[postorder[postorder_root]];
// 建立根节点
TreeNode root = new TreeNode(postorder[postorder_root]);
//子树大小
int size_left_subtree = inorder_root - inorder_left;
//递归建树
root->left = myBuildTree(postorder, inorder, postorder_left,
postorder_left + size_left_subtree - 1, inorder_left, inorder_root - 1);
root->right = myBuildTree(postorder, inorder, postorder_left + size_left_subtree,
postorder_right - 1, inorder_root + 1, inorder_right);
return root;
}
// 思路1
//TreeNode* buildTree(vector& inorder, vector& postorder) {
// if (inorder.size() == 0)return NULL;
// TreeNode* r = new TreeNode(postorder.back());
// cout <<“根:”<val << endl;
// if (postorder.size() == 1)
// {
// r->left = NULL;
// r->right = NULL;
// return r;
// }
// int i = 0;
// vector l_in;
// vector r_in;
// int in_len = inorder.size();
// // 左子树的中序遍历 找到根
// while (inorder[i] != r->val)
// {
// l_in.emplace_back(inorder[i]);
// i++;
// }
// i++; //跳过根节点
// //右子树的中序遍历
// while (i <= in_len - 1) {
// r_in.emplace_back(inorder[i]);
// i++;
// }
// int j = 0;
// vector l_post;
// vector r_post;
// int post_len = postorder.size();
// // 左子树的后序遍历
// int l_len = l_in.size();
// int k = 0;
// while (k < l_len)
// {
// l_post.emplace_back(postorder[j]);
// j++;
// k++;
// }
// //右子树的后序遍历
// while (j < post_len-1)
// {
// r_post.emplace_back(postorder[j]);
// j++;
// }
// //递归生成左右子树
// //左子树中序遍历
// cout << “左子树:”;
// for (auto i : l_in)
// {
// cout << i;
// }
// cout << " ";
// //左子树后序遍历
// for (auto i : l_post)
// {
// cout << i;
// }
// cout << endl;
// cout << “右子树:”;
// //右子树中序遍历
// for (auto i : r_in)
// {
// cout << i;
// }
// cout << " “;
// //右子树后序遍历
// for (auto i : r_post)
// {
// cout << i;
// }
// cout << endl;
// r->left = buildTree(l_in,l_post);
// r->right = buildTree(r_in,r_post);
// return r;
//}
// 优化
TreeNode* buildTree(vector& inorder, vector& postorder) {
int n = postorder.size();
for (int i = 0; i < n; i++) {
index[inorder[i]] = i;
}
return myBuildTree(postorder, inorder, 0, n - 1, 0, n - 1);
}
};
void PreOrder(TreeNode* T)
{
if (T != NULL)
{
printf(”%d ", T->val);
PreOrder(T->left);//递归先序遍历左右子树
PreOrder(T->right);
}
}
//主函数
int main()
{
vector inorder { 9,3,15,20,7 };
vector postorder { 9,15,7,20,3 };
Solution s;
TreeNode* T = s.buildTree(inorder,postorder);
PreOrder(T);
cout << endl;
return 0;
}
## 相关题目
[LeetCode889 根据前序和后序遍历构造二叉树]( )
[LeetCode105 从前序与中序遍历序列构造二叉树]( )
更多内容:[OJ网站题目分类,分难度整理笔记(leetcode、牛客网)]( )