(三十四)找到二叉树中的最大搜索二叉树

给定一个二叉树,要求找到其中节点数最多的搜索二叉树,要求时间复杂度为O(N),额外空间复杂度为O(h)。解题思路采用树形动态规划,通过分析三种可能的情况:答案可能来自左子树、右子树或整个子树。通过递归函数获取左、右子树的信息,包括最大搜索二叉子树的头部、大小以及最大值和最小值,最终确定最大搜索二叉子树。
摘要由CSDN通过智能技术生成

【题目】给定一棵二叉树的头节点head,已知其中所有节点的值都不一样,找到含有节点最多的搜索二叉树,并返回这颗子树的头节点。

在这里插入图片描述

【要求】如果节点数为N,要求时间复杂度为O(N),额外空间复杂度为O(h),h为二叉树的高度

【解题】树形dp套路

第一步:分析答案的可能性

  • 第一种:X为头节点的子树中,最大的搜索二叉树就是X的左子树中的最大搜索二叉子树。即答案来自左子树
  • 第二种:X为头节点的子树中,最大的搜索二叉树就是X的右子树中的最大搜索二叉子树。即答案来自右子树
  • 第三种:若X左子树上的最大搜索二叉子树是X左子树的全体,X右子树上的最大搜索二叉子树是X右数全体,并且X的值大于X的左子树所有节点的最大值,且小于X右子树所有节点的最小值,那么X为头节点的子树中,最大的搜索二叉子树是以X为头节点的全体。

第二步:列出需要的信息

  • 若为第一种、第二种情况,则需要知道左子树和右子树上的最大搜索二叉子树的头部,记为;leftBSTHead,rightBSTHead;
  • 左子树和右子树上最大二叉搜索子树的大小,记为leftBSTSize,rightBSTSize;
  • 左子树的最大值和右子树的最小值,leftMax,rightMin

第三步:整合信息
左右子树都需要最大搜索二叉子树的头节点以及大小这两个信息,但是左子树只需要最大值,右子树只需要最小值,那么合并变成统一要求:左右子树的最大值和最小值

struct ReturnType{
   
    TreeNode* maxBSRHead;
    int maxBSTSize;
    int minValue;
    int maxValue;

    ReturnType(TreeNode* maxBSRHead,int maxBSTSize,int minValue,int maxValue){
   
        this->maxBSRHead = maxBSRHead;
        this->maxBSTSize = maxBSTSize;
        this->minValue = minValue;
        this->maxValue = maxValue;
    }
}; 

第四步:设计递归函数,包括递归的base case,默认得到左树和右树的所有信息,整合信息,返回第三步的信息结构这四个步骤

ReturnType* process(TreeNode* X){
   
    /*base case:若子树为空,最小值为系统最大,最大值为系统最小*/
    if(X == NULL)
        return new ReturnType(NULL,0,INT_MAX,INT_MIN);
    /*默认得到左右子树的所有信息*/
    ReturnType* lData = process(X->left);
    ReturnType* rData = process(X->right);

    /*信息整合*/
    int minValue = min(X->value,min(lData->minValue,rData->minValue));
    int maxValue 
  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值