day09二叉树3

617.合并二叉树

TreeNode* mergeTrees(TreeNode* t1, TreeNode* t2) {
        if (t1 == NULL) return t2; // 如果t1为空,合并之后就应该是t2
        if (t2 == NULL) return t1; // 如果t2为空,合并之后就应该是t1
        // 修改了t1的数值和结构
        t1->val += t2->val;                             // 中
        t1->left = mergeTrees(t1->left, t2->left);      // 左
        t1->right = mergeTrees(t1->right, t2->right);   // 右
        return t1;
    }

如上的方法修改了t1的结构,当然也可以不修改t1和t2的结构,重新定义一个树。

不修改输入树的结构,前序遍历,代码如下:

TreeNode* mergeTrees(TreeNode* t1, TreeNode* t2) {
        if (t1 == NULL) return t2;
        if (t2 == NULL) return t1;
        // 重新定义新的节点,不修改原有两个树的结构
        TreeNode* root = new TreeNode(0);
        root->val = t1->val + t2->val;
        root->left = mergeTrees(t1->left, t2->left);
        root->right = mergeTrees(t1->right, t2->right);
        return root;
    }

700.二叉搜索树中的搜索

 TreeNode* searchBST(TreeNode* root, int val) {
        if(root==nullptr||root->val==val) return root;
        TreeNode* result=nullptr;
        if(root->val>val) result=searchBST(root->left,val);
        if(root->val<val) result=searchBST(root->right,val);
        return result;
    }

迭代法:

reeNode* searchBST(TreeNode* root, int val) {
        while (root != NULL) {
            if (root->val > val) root = root->left;
            else if (root->val < val) root = root->right;
            else return root;
        }
        return NULL;
    }

98.验证二叉搜索树

vector<int> vec;
    void traversal(TreeNode* root){
        if(root == NULL) return;
        traversal(root->left);
        vec.push_back(root->val);// 将二叉搜索树转换为有序数组
        traversal(root->right);
    }
    bool isValidBST(TreeNode* root) {
        vec.clear();
        traversal(root);
        for(int i = 1; i < vec.size(); i++){
            // 注意要小于等于,搜索树里不能有相同元素
            if(vec[i] <= vec[i-1]) return false;
        }
        return true;
    }

要定义一个longlong的全局变量,用来比较遍历的节点是否有序,因为后台测试数据中有int最小值,所以定义为longlong的类型,初始化为longlong最小值。

long long maxVal = LONG_MIN;// 因为后台测试数据中有int最小值
    bool isValidBST(TreeNode* root) {
        if(root == NULL) return true;
        
        bool left = isValidBST(root->left);
        // 中序遍历,验证遍历的元素是不是从小到大
        if (maxVal < root->val) maxVal = root->val;
        else return false;
        bool right = isValidBST(root->right);

        return left && right;
    }

以上代码是因为后台数据有int最小值测试用例,所以都把maxVal改成了longlong最小值。

如果测试数据中有 longlong的最小值,怎么办?

不可能在初始化一个更小的值了吧。 建议避免 初始化最小值,如下方法取到最左面节点的数值来比较。

TreeNode* pre = NULL; // 用来记录前一个节点
    bool isValidBST(TreeNode* root) {
        if(root == NULL) return true;
        bool left = isValidBST(root->left);
        // 中序遍历,验证遍历的元素是不是从小到大
        if (pre!=NULL && pre->val >= root->val) 
            return false;
        pre=root;// 记录前一个节点
        bool right = isValidBST(root->right);
        return left && right;
    }

530.二叉搜索树的最小绝对差

vector<int> vec;
void traversal(TreeNode* root) {
    if (root == NULL) return;
    traversal(root->left);
    vec.push_back(root->val); // 将二叉搜索树转换为有序数组
    traversal(root->right);
}    
    int getMinimumDifference(TreeNode* root) {
        vec.clear();
        traversal(root);
        if (vec.size() < 2) return 0;
        int result = INT_MAX;
        for (int i = 1; i < vec.size(); i++) { // 统计有序数组的最小差值
            result = min(result, vec[i] - vec[i-1]);
        }
        return result;
    }

双指针

TreeNode* pre = NULL; // 用来记录前一个节点
    int result = INT_MAX;
    void traversal(TreeNode* cur){
        if(cur == NULL) return;
        traversal(cur->left); // 左
        if(pre != NULL) result=min(result,cur->val - pre->val);// 中
        pre = cur;// 记录前一个
        traversal(cur->right);// 右
    }
    int getMinimumDifference(TreeNode* root) {
        traversal(root);
        return result;
    }

501.二叉搜索树中的众数

class Solution {
public:
    int maxCount=0;// 最大频率
    int count=0;// 统计频率
    TreeNode* pre=NULL;
    vector<int> result;
    void searchBST(TreeNode* cur) {
        if(cur==NULL) return;
        searchBST(cur->left);       // 左
        //中
        if(pre==NULL) // 第一个节点
            count=1;
        else if(pre->val==cur->val) // 与前一个节点数值相同
            count++;
        else // 与前一个节点数值不同
            count=1;
        pre=cur;// 更新上一个节点
        if(count==maxCount) result.push_back(cur->val);// 如果和最大值相同,放进result中
        if(count>maxCount){// 如果计数大于最大值频率
            maxCount=count;// 如果计数大于最大值频率
            result.clear();// 很关键的一步,不要忘记清空result,之前result里的元素都失效了
            result.push_back(cur->val);
        }
        searchBST(cur->right);      // 右
        return ;
        
    }
    vector<int> findMode(TreeNode* root) {
        count = 0;
        maxCount = 0;
        pre = NULL; // 记录前一个节点
        result.clear();
        
        searchBST(root);
        return result;
    }
};

236. 二叉树的最近公共祖先

TreeNode* lowestCommonAncestor(TreeNode* root, TreeNode* p, TreeNode* q) {
        if(root == q || root ==p || root ==NULL) return root;
        TreeNode* left = lowestCommonAncestor(root->left,p,q);
        TreeNode* right=lowestCommonAncestor(root->right,p,q);
        if(left!=NULL && right!=NULL) return root;
        else if(left == NULL && right != NULL) return right;
        else if(left != NULL && right == NULL) return left;
        else{//  (left == NULL && right == NULL)
            return NULL;
        }
    }
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值