二叉树相关oj题——2.另一棵树的子树(Java实现)

文章介绍了如何使用Java实现一个名为`isSubtree`的方法,判断给定的二叉树B是否为二叉树A的子树。方法涉及递归遍历,以及对空指针异常的修正。重点在于`isSameTree`方法的逻辑,通过比较节点值和子节点结构来确定两棵树的相似性。
摘要由CSDN通过智能技术生成

题目链接另一颗树的子树
解题思路
1.有两棵树A、B,其根节点分别为root和subRoot。先判断A和B是否相同,如果相同,返回true;否则进入第2步;
在这里插入图片描述
2.判断树B是不是A的左子树,如果是,返回true;否则,再判断B是不是A的右子树,如果是,返回true;如果不是,此时B既不是A的左子树又不是A的右子树,则B不是A的子树,返回false。举例图示如下:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
代码实现

/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode() {}
 *     TreeNode(int val) { this.val = val; }
 *     TreeNode(int val, TreeNode left, TreeNode right) {
 *         this.val = val;
 *         this.left = left;
 *         this.right = right;
 *     }
 * }
 */
class Solution {
    public boolean isSubtree(TreeNode root, TreeNode subRoot) {    
    	 //判断以root为根节点的树和以subRoot为根节点的树是否相同
        if(isSameTree(root,subRoot)){
            return true;
        }
        //以subRoot为根的树是以root为根的树的左子树
        if(isSubtree(root.left,subRoot)){
            return true;
        }
        以subRoot为根的树是以root为根的树的右子树
        if(isSubtree(root.right,subRoot)){
            return true;
        }
        //走到这里时,subRoot树与root树几部相同,也不是其左子树或右子树
        return false;
    }
    //判断以p节点为根节点的树和以q节点为根节点的树是否相同
    public boolean isSameTree(TreeNode p, TreeNode q) {
        //思路:对p树和q树的根节点
        //1、如果一个为空,一个不为空,两棵树不同;
        //2、如果两个都为空,返回true;
        //3、如果两个都不为空,且值不同,则两棵树不同;
        //4、如果两个都不为空,且值相同,则继续判断
        //p.left与q.left,p.right与p.right是否相同,如果两者都相同,则两棵树相同,否则不相同
        if(p == null && q != null  || p != null && q == null){
            return false;
        }
        if(p == null && q == null){
            return true;
        }
        //走到这里时,p、q都不为空
        if(p.val != q.val){
            return false;
        }
        //走到这里,p、q都不为空且值相同
        return isSameTree(p.left,q.left) && isSameTree(p.right,q.right);
    }
}

说明:public boolean isSameTree(TreeNode p, TreeNode q)方法是手动写的一个方法,用于判断以p为根节点的树和以q为根节点的树是否相同(内容上的相同)。
程序运行结果如下:
在这里插入图片描述
分析:出现空指针异常。原因是没有对参数root是否为null做出判断。如果root == null而subRoot != null,则会在第2个if语句条件判断部分发生空指针异常。
debug:由于当 root == null 且subRoot == null的情况,已经在第一个if语句中进行执行判断了,我们只需补充root == null且subRoot != null的情况。即在第一个if语句之后补充如下语句即可:

if(root == null && subRoot != null){
      return false;
}

最终代码如下:

/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode() {}
 *     TreeNode(int val) { this.val = val; }
 *     TreeNode(int val, TreeNode left, TreeNode right) {
 *         this.val = val;
 *         this.left = left;
 *         this.right = right;
 *     }
 * }
 */
class Solution {
    public boolean isSubtree(TreeNode root, TreeNode subRoot) {    
        if(isSameTree(root,subRoot)){
            return true;
        }
        if(root == null && subRoot != null){
            return false;
        }
        if(isSubtree(root.left,subRoot)){
            return true;
        }
        if(isSubtree(root.right,subRoot)){
            return true;
        }
        return false;
    }
    //判断以p节点为根节点的树和以q节点为根节点的树是否相同
    public boolean isSameTree(TreeNode p, TreeNode q) {
        //思路:对p树和q树的根节点
        //1、如果一个为空,一个不为空,两棵树不同;
        //2、如果两个都为空,返回true;
        //3、如果两个都不为空,且值不同,则两棵树不同;
        //4、如果两个都不为空,且值相同,则继续判断
        //p.left与q.left,p.right与p.right是否相同,如果两者都相同,则两棵树相同,否则不相同
        if(p == null && q != null  || p != null && q == null){
            return false;
        }
        if(p == null && q == null){
            return true;
        }
        //走到这里时,p、q都不为空
        if(p.val != q.val){
            return false;
        }
        //走到这里,p、q都不为空且值相同
        return isSameTree(p.left,q.left) && isSameTree(p.right,q.right);
    }
}
  • 12
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
判断一个二叉树是否为另一棵树子树,可以采用递归的方法,先判断当前根节点是否相同,若相同则递归判断左右子树是否相同,若不同则递归判断原二叉树的左右子树是否为目标树的子树。 具体实现步骤如下: 1. 判断当前节点是否为空,若为空则返回 false。 2. 判断当前节点是否与目标树的根节点相同,若相同则递归判断左右子树是否相同。 3. 若当前节点与目标树的根节点不同,则递归判断原二叉树的左右子树是否为目标树的子树。 具体实现代码如下(假设 TreeNode 为二叉树节点的数据结构): ``` bool isSubtree(TreeNode* s, TreeNode* t) { if (!s) return false; // 若当前节点为空,返回 false if (isSameTree(s, t)) return true; // 若当前节点与目标树根节点相同,递归判断左右子树是否相同 return isSubtree(s->left, t) || isSubtree(s->right, t); // 若不同,则递归判断原二叉树的左右子树是否为目标树的子树 } bool isSameTree(TreeNode* p, TreeNode* q) { if (!p && !q) return true; // 若两个节点均为空,返回 true if (!p || !q) return false; // 若其中一个节点为空,返回 false if (p->val != q->val) return false; // 若两个节点的值不同,返回 false return isSameTree(p->left, q->left) && isSameTree(p->right, q->right); // 递归判断左右子树是否相同 } ``` 其中 isSameTree 函数用于判断两个节点以及它们的子树是否相同。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值