/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode() : val(0), left(nullptr), right(nullptr) {}
* TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
* TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
* };
*/
class Solution {
public:
vector<TreeNode*> allPossibleFBT(int n) {
vector<TreeNode*> v;
if (n == 0)
return v;
if (n == 1) {
TreeNode* tree = new TreeNode(0);
v.push_back(tree);
return v;
}
for (int i = 0; i < n; i++) {
vector<TreeNode*> v_Left;
vector<TreeNode*> v_Right;
v_Left = allPossibleFBT(i);
v_Right = allPossibleFBT(n-i-1);
for (TreeNode* tmpLeft : v_Left) {
for (TreeNode* tmpRight : v_Right) {
TreeNode* tree = new TreeNode(0);
tree->left = tmpLeft;
tree->right = tmpRight;
v.push_back(tree);
}
}
}
return v;
}
};
要点
使用递归的思想,树的构造直接返回一个树的结构可以实现递归,但是该题返回树的列表,没有办法直观的用递归;
解决方法:
创建临时变量(该题中为vector数组),利用递归解决问题之后,将其返回,那么此时每个子问题返回的也是vector数组,因而需要追加处理的部分(该题中将两个子问题的树合并成一个大的树的数组)
但是上述方法存在子问题的重复计算,造成超时;见下:
/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode() : val(0), left(nullptr), right(nullptr) {}
* TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
* TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
* };
*/
class Solution {
public:
map<int, vector<TreeNode*>> m;
vector<TreeNode*> allPossibleFBT(int n) {
vector<TreeNode*> v;
if (n == 0)
return v;
if (n == 1) {
TreeNode* tree = new TreeNode(0);
v.push_back(tree);
return v;
}
for (int i = 0; i < n; i++) {
vector<TreeNode*> v_Left;
vector<TreeNode*> v_Right;
if (m.find(i) != m.end()) {
v_Left = m[i];
} else {
v_Left = allPossibleFBT(i);
}
if (m.find(n-i-1) != m.end()) {
v_Right = m[n-1-i];
} else {
v_Right = allPossibleFBT(n-i-1);
}
for (TreeNode* tmpLeft : v_Left) {
for (TreeNode* tmpRight : v_Right) {
TreeNode* tree = new TreeNode(0);
tree->left = tmpLeft;
tree->right = tmpRight;
v.push_back(tree);
}
}
}
m[n] = v;
return v;
}
};
要点
我们使用一个map,记录子问题的结果(此题为节点个数和树的vector数组);
在递归逻辑之前进行判断,如果有结果了,则直接取出来,否则递归,并把所得结果放入map之中;
map必须放在函数外面,作为全局变量使用,才能起到保存结果的效果;
判断是否存在某个key,使用find方法;使用数组形式进行访问k-v(关联式数组)
注意体会递归的思想;