0.问题
给定两个非空二叉树 s 和 t,检验 s 中是否包含和 t 具有相同结构和节点值的子树。s 的一个子树包括 s 的一个节点和这个节点的所有子孙。s 也可以看做它自身的一棵子树。
链接
1.实现
/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode(int x) : val(x), left(NULL), right(NULL) {}
* };
*/
class Solution {
public:
//方案1:递归源树的每个节点,以此节点起始逐个节点对比两棵树
bool isEqual(TreeNode* s, TreeNode* t) {
if(s == NULL && t == NULL)
return true;
if(s == NULL || t == NULL)
return false;
if(s->val == t->val)
return isEqual(s->left, t->left) && isEqual(s->right, t->right);
else
return false;
}
bool isSubtree1(TreeNode* s, TreeNode* t) {
if(s == NULL && t == NULL)
return true;
if(s == NULL || t == NULL)
return false;
if(isEqual(s, t))
return true;
return isSubtree(s->left, t) || isSubtree(s->right, t);
}
//方案2:先序遍历两棵树,从中寻找匹配的序列
void travlTree(TreeNode* root, vector<int> &list) {
if(root == NULL) {
list.push_back(65535); //这个需要赋值最大值,如果树中有此值,此方法失效
return;
}
list.push_back(root->val);
travlTree(root->left, list);
travlTree(root->right, list);
}
bool isSubtree(TreeNode* s, TreeNode* t) {
vector<int> ls, lt;
travlTree(s, ls);
travlTree(t, lt);
int i, j;
//注意等号
for(i = 0; i <= ls.size() - lt.size(); ++i) {
if(ls[i] == lt[0]) {
for(j = 1; j < lt.size(); ++j) {
if(ls[i + j] != lt[j])
break;
}
if(j == lt.size())
return true;
}
}
return false;
}
};
2. 优化
其中方案2寻找子序列可以优化,等价于寻找字符串的子串问题。