方法一:利用辅助队列 以广度优先的顺序将 节点依次存入辅助队列中
class Solution {
public:
TreeNode* mirrorTree(TreeNode* root) {
if(!root) return NULL;
queue<TreeNode*> a;
a.push(root);
while(!a.empty())
{
TreeNode *temp = a.front();
a.pop();
TreeNode *t = temp->left;
temp->left = temp->right;
temp->right = t;
if(temp->left) a.push(temp->left);
if(temp->right) a.push(temp->right);
}
return root;
}
};
方法二:利用递归
递归函数需要具备的条件:(1)结束条件 (2)调用自身 (3)返回值
class Solution {
public:
TreeNode* mirrorTree(TreeNode* root) {
if(!root) return root;
TreeNode *temp = root->left;
root->left = root->right;
root->right = temp;
mirrorTree(root->left);
mirrorTree(root->right);
return root;
}
};
思路:利用递归
首先需要函数 判断以a为根的子树 与以b为根的子树 是否一致的函数 judge
如果以a为根的子树 与以b为根的子树不一致,那么看以a->left为根的子树 与以b为根的子树 是否一致 和以a->right为根的子树 与以b为根的子树 是否一致
class Solution {
//判断以a为根的子树 与以b为根的子树 是否一致
bool judge(TreeNode *a, TreeNode *b)
{
if(!b) return true;
if(!a || a->val != b->val) return false;
return judge(a->left, b->left)&&judge(a->right, b->right);
}
public:
bool isSubStructure(TreeNode* A, TreeNode* B) {
if(!A || !B) return false;
if(judge(A, B)) return true;
return isSubStructure(A->left, B)|| isSubStructure(A->right, B);
}
};
leetcode98 98. 验证二叉搜索树
假设一个二叉搜索树具有如下特征:
- 节点的左子树只包含小于当前节点的数。
- 节点的右子树只包含大于当前节点的数。
- 所有左子树和右子树自身必须也是二叉搜索树。
递归函数:的入参要包含当前子树的 数值范围
class Solution {
bool isSearchTree(TreeNode *root, long minVal, long maxVal)
{
if(!root) return true;
if(root->val <= minVal || root->val >= maxVal) return false;
return isSearchTree(root->left, minVal, root->val) && isSearchTree(root->right, root->val, maxVal);
}
public:
bool isValidBST(TreeNode* root) {
return isSearchTree(root, LONG_MIN, LONG_MAX);
}
};
leetcode450. 删除二叉搜索树中的节点
思路:由于二叉搜索树是满足左子树的值均小于根节点的值 ,右子树的值均大于根节点的值,利用递归
class Solution {
TreeNode* findMinNode(TreeNode* root) //找到以root为根节点的最小值
{
while(root->left)
{
root = root->left;
}
return root;
}
public:
TreeNode* deleteNode(TreeNode* root, int key) {
if(!root) return root;
if(key < root->val) //key在root的左子树中
{
root->left = deleteNode(root->left, key);
}
else if(key > root->val)//key在root的右子树中
{
root->right = deleteNode(root->right, key);
}
else//root->val == key 此时要做删除节点操作
{
//左子树为空 或者右子树为空 或者左右子树均为空
if(!root->left) return root->right;
if(!root->right) return root->left;
//左右子树均不为空 首先找到右子树中的最小值,然后将root->val替换为该值 然后删除右子树中的最小值
TreeNode * temp = findMinNode(root->right);
root->val = temp->val;
root->right = deleteNode(root->right, root->val);
}
return root;
}
};
leetcode103. 二叉树的锯齿形层序遍历
思路:利用辅助队列,只不过需要对临时数组进行逆序操作
class Solution {
public:
vector<vector<int>> zigzagLevelOrder(TreeNode* root) {
vector<vector<int>> res;
if(!root) return res;
queue<TreeNode*> a;
a.push(root);
int line = 0;
while(!a.empty())
{
int size = a.size();
vector<int> tmp;
while(size--)
{
TreeNode *temp = a.front();
a.pop();
tmp.push_back(temp->val);
if(temp->left) a.push(temp->left);
if(temp->right) a.push(temp->right);
}
if(line%2 == 1)
{
reverse(tmp.begin(), tmp.end());
}
line++;
res.push_back(tmp);
}
return res;
}
};
思路:利用递归
注意:该路径要既包含root还要包含叶节点 对于树 [1, 2] 如果target为1 虽然 1== 树的root但是,该路径不包含叶节点,所以也返回false
class Solution {
vector<vector<int>> res;
public:
void dfs(TreeNode *root, int target, vector<int>& temp)
{
if(!root) return;
if(target == root->val && !root->left && !root->right) //说明已经找到该路径
{
temp.push_back(root->val); //注意 在临时数组中push一次 就要进行pop
res.push_back(temp);
temp.pop_back();
}
else
{
temp.push_back(root->val);
if(root->left) dfs(root->left, target - root->val, temp);
if(root->right) dfs(root->right, target - root->val, temp);
temp.pop_back();
}
}
vector<vector<int>> pathSum(TreeNode* root, int target) {
if(!root) return {};
vector<int> temp;
dfs(root, target, temp);
return res;
}
};
思路:利用递归 求左子树和右子树的高度
class Solution {
public:
int maxDepth(TreeNode* root) {
if(!root) return 0;
int leftHight = maxDepth(root->left);
int rightHight = maxDepth(root->right);
return max(leftHight, rightHight) + 1;
}
};
leetcode111:二叉树最小高度
思路:利用递归,但需要注意的是:比如,当root->left为空,但是root->right不为空时,二叉树的最小高度不能为1,因为在二叉树的最小高度时,要包含至少一个叶节点
class Solution {
public:
int minDepth(TreeNode* root) {
if(!root) return 0;
if(!root->left && !root->right) //左右子树都为空
{
return 1;
}
else if(!root->left && root->right)//左子树为空 右子树不为空
{
int right = minDepth(root->right);
return right + 1;
}
else if(root->left && !root->right)//右子树为空 左子树不为空
{
int left = minDepth(root->left);
return left+1;
}
else //左右子树均不为空
{
int left = minDepth(root->left);
int right = minDepth(root->right);
return min(left, right) + 1;
}
}
};