剑指offer17--树的子结构

题目描述

输入两棵二叉树A,B,判断B是不是A的子结构。(ps:我们约定空树不是任意一个树的子结构)

思路

对于判断树的结构相关的,一般都是可以用递归的。既然要用递归,就要考虑递归的返回条件。
首先在第一次进入代码块的时候,根据题意,只要p2不存在就直接返回false,另一个,当p1不存在的时候也返回false。
但是,递归何时返回呢?当然是p2到底了,返回true,如果p2还没到底,p1已经到底了,当然是返回false.

这就带来了冲突,p2第一次进入为空就返回0,但是后续递归却要用到它是否为空。于是我们想到将这个递归放到另一个函数里面。

整体思路:
入口值相等,继续往下判断(这一部分在新的递归代码块实现);
入口值不相等,将p1的左子树和右子树分别与p2传进主代码块递归

实现

class Solution {
public:
    bool dfs(TreeNode* p1,TreeNode* p2)
    {
        if (!p2) return 1;
        if (!p1) return 0;
        
        return (p1->val==p2->val)
            &&dfs(p1->left,p2->left)
            &&dfs(p1->right,p2->right);
            //根结点相等时要左右子树全部满足才返回真
    }
    bool HasSubtree(TreeNode* pRoot1, TreeNode* pRoot2)
    {
        if (!pRoot1||!pRoot2) return 0;//第一次进入只要有空就返回false
        return dfs(pRoot1,pRoot2)//根结点相等判断
            ||HasSubtree(pRoot1->left, pRoot2)//左子树自身递归
            ||HasSubtree(pRoot1->right, pRoot2);//右子树自身递归
            //上面只要有一个满足就返回true
    }
};

教训

在寻找递归返回条件时被上述的冲突给困住了。

对于这样的一个需求:
如果某种条件在第一次之后可以满足,但是第一次却不能满足,就要考虑新建一个递归函数

这里,p2==NULL时,返回false,如果这时候返回后面就无法进行了,但是后续却要依赖它为NULL来控制递归的返回。于是另外新建一个递归函数。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值