题目描述:
输入两棵二叉树A,B,判断B是不是A的子结构。(ps:我们约定空树不是任意一个树的子结构)
思路:
-
递归法: 对于给定的两棵二叉树来判断B是否是A的子结构,要充分考虑以下几种情形:
- 若A和B中有一棵为空则两者之间必不存在结构,返回False
- 若A和B均不为空,则要先在A中找到和B根节点相同的节点,然后判断它们的子节点是否相同,直到到达A或B的叶子节点
- 根据二叉树本身的性质,整个过程可以使用递归完成
-
先序遍历法:如果B是A的子结构,那么B的先序遍历结果就是A的先序遍历结果的一部分。因此可以先通过先序遍历获取两棵树的遍历结果,然后进行即可
AC代码
递归法
# -*- coding:utf-8 -*-
# class TreeNode:
# def __init__(self, x):
# self.val = x
# self.left = None
# self.right = None
class Solution:
def HasSubtree(self, pRoot1, pRoot2):
# write code here
def hasEqual(root1, root2):
# 若小树只有相同的根节点,则返回True
if root2 == None:
return True
# 如果大树只有根节点,而小树还有子节点,返回False
if root1 == None:
return False
# 若根节点相同
if root1.val ==root2.val:
# 如果小树不存在左子树,表示已判断部分相同,子结构成立,返回True
if root2.left == None:
leftEqual = True
else:
# 往下递归判断
leftEqual = hasEqual(root1.left, root2.left)
# 如果小树右节点为空,判断终止,已判断部分相同,子结构成立,返回True
if root2.right == None:
rightEqual = True
else:
# 往下递归判断
rightEqual = hasEqual(root1.right, root2.right)
# 如果都为True说明子结构成立
return leftEqual and rightEqual
# 如果当前节点为根节点都不同,直接返回False
return False
# 如果有一棵为空直接返回False
if pRoot1 == None or pRoot2 == None:
return False
# 如果A和B的根节点就相同,递归判断子节点
if pRoot1.val == pRoot2.val:
ret = hasEqual(pRoot1, pRoot2)
if ret:
return True
# 在A的左子树找和B的根节点相同的子节点再进行判断
ret = self.HasSubtree(pRoot1.left, pRoot2)
if ret:
return True
# 在A的右子树找和B的根节点相同的子节点再进行判断
ret = self.HasSubtree(pRoot1.right, pRoot2)
return ret
先序遍历法
# -*- coding:utf-8 -*-
# class TreeNode:
# def __init__(self, x):
# self.val = x
# self.left = None
# self.right = None
class Solution:
def __init__(self):
self.res1 = []
self.res2 = []
def HasSubtree(self, pRoot1, pRoot2):
# write code here
def preOrder(flag, root):
if root == None:
return None
if flag == 1:
self.res1.append(root.val)
else:
self.res2.append(root.val)
preOrder(flag, root.left)
preOrder(flag, root.right)
if pRoot1 == None or pRoot2 == None:
return False
preOrder(1, pRoot1)
preOrder(2, pRoot2)
for i in range(len(self.res1)):
if self.res1[i] == self.res2[0] and self.res1[i:i + len(self.res2)] == self.res2:
return True
return False