[CareerCup] 4.8 Contain Tree 包含树

4.8 You have two very large binary trees: Tl, with millions of nodes, and T2, with hundreds of nodes. Create an algorithm to decide if T2 is a subtree of Tl. A tree T2 is a subtree of Tl if there exists a node n in Tl such that the subtree of n is identical to T2. That is, if you cut off the tree at node n, the two trees would be identical.

这道题给我们两棵树,T1和T2,其中T1有百万个节点,T2有上百个节点,让我们写算法来判断T2是不是T1的子树。首先可以用的方法是,我们对两棵树分别进行前序和中序遍历,然后把结果分别存入字符串中,如果T2的前序和中序遍历的字符串分别是T1的前序和中序遍历的字符串的子串,那么我们可以判定T2是T1的子树,参见代码如下:

解法一:

class Solution {
public:
    bool containTree(TreeNode *root1, TreeNode *root2) {
        string pre1, pre2, in1, in2;
        preorder(root1, pre1);
        preorder(root2, pre2);
        inorder(root1, in1);
        inorder(root2, in2);
        if (pre1.find(pre2) == pre1.size() - pre2.size() && in1.find(in2) == in1.size() - in2.size()) return true;
        else return false;
    }
    void preorder(TreeNode *root, string &res) {
        if (!root) return;
        res.append(to_string(root->val));
        preorder(root->left, res);
        preorder(root->right, res);
    }
    void inorder(TreeNode *root, string &res) {
        if (!root) return;
        inorder(root->left, res);
        res.append(to_string(root->val));
        inorder(root->right, res);
    }
};

但是上面这种解法存在例外情况无法正确分辨,比如下面的两棵树:

3                       3

/           and            \

3                                 3

它们的中序和前序遍历都相同,所以上述算法会返回true,但我们知道它们是两个不同的树,谁也不包含谁,谁也不是谁的子树。Cracking the Coding Interview 5th Edition这书上第235页上说我们可以标记处空节点,但这种方法麻烦,又占空间,所以这里我不去写它。下面来看书上给出的另一种解法,这种解法的思路是,我们首先判断T2是否为空,为空则直接返回True,因为空树是任何树的子树,然后我们看T1是否为空,T1为空直接返回false,因为空树不可能有非空子树,然后我们看两个根节点的值是否相同,如果相同,则调用matchTree方法,来比较整个T2树,如果完全匹配则返回true,否则继续往下递归,参见代码如下:

解法二:

class Solution {
public:
    bool containTree(TreeNode *root1, TreeNode *root2) {
        if (!root2) return true;
        if (!root1) return false;
        if (root1->val == root2->val) {
            if (matchTree(root1, root2)) return true;
        }
        return containTree(root1->left, root2) || containTree(root1->right, root2);
    }
    bool matchTree(TreeNode *root1, TreeNode *root2) {
        if (!root1 && !root2) return true;
        if (!root1 || !root2) return false;
        if (root1->val != root2->val) return false;
        else (matchTree(root1->left, root2->left) && matchTree(root1->right, root2->right));
    }
};
时间: 2024-10-08 19:41:39

[CareerCup] 4.8 Contain Tree 包含树的相关文章

[转] Splay Tree(伸展树)

好久没写过了,比赛的时候就调了一个小时,差点悲剧,重新复习一下,觉得这个写的很不错.转自:here Splay Tree(伸展树) 二叉查找树(Binary Search Tree)能够支持多种动态集合操作.因此,在信息学竞赛中,二叉排序树起着非常重要的作用,它可以被用来表示有序集合.建立索引或优先队列等. 作用于二叉查找树上的基本操作的时间是与树的高度成正比的.对一个含n各节点的完全二叉树,这些操作的最坏情况运行时间为O(log n).但如果树是含n个节点的线性链,则这些操作的最坏情况运行时间

HDU 4718 The LCIS on the Tree(树链剖分)

Problem Description For a sequence S1, S2, ... , SN, and a pair of integers (i, j), if 1 <= i <= j <= N and Si < Si+1 < Si+2 < ... < Sj-1 < Sj , then the sequence Si, Si+1, ... , Sj is a CIS(Continuous Increasing Subsequence). The

HDU 4107 Gangster Segment Tree线段树

这道题也有点新意,就是需要记录最小值段和最大值段,然后成段更新这个段,而不用没点去更新,达到提高速度的目的. 本题过的人很少,因为大部分都超时了,我严格按照线段树的方法去写,一开始居然也超时. 然后修补了两个地方就过了,具体修改的地方请参看程序. 知道最大值段和最小值段,然后修补一下就能过了.不是特别难的题目. #include <stdio.h> #include <string> #include <algorithm> using namespace std; c

Geeks Splay Tree Insert 树的插入操作

Splay树的插入操作,只需要处理好插入节点的孩子节点就可以了,最重要的是不要破坏了BST的基本规则. 因为高度并不是Splay树的首要因素,所以插入的时候也是使用splay操作,然后在根节点插入. 参考:http://www.geeksforgeeks.org/splay-tree-set-2-insert-delete/ 对比一下使用插入创建的树和手工创建数的区别,先序遍历的结果: #pragma once #include<stdio.h> #include <stdlib.h&g

【HDOJ 5834】Magic boy Bi Luo with his excited tree(树型DP)

[HDOJ 5834]Magic boy Bi Luo with his excited tree(树型DP) Magic boy Bi Luo with his excited tree Time Limit: 8000/4000 MS (Java/Others)    Memory Limit: 131072/131072 K (Java/Others) Problem Description Bi Luo is a magic boy, he also has a migic tree,

poj 3321:Apple Tree(树状数组,提高题)

Apple Tree Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 18623   Accepted: 5629 Description There is an apple tree outside of kaka's house. Every autumn, a lot of apples will grow in the tree. Kaka likes apple very much, so he has been

【POJ 2486】 Apple Tree(树型dp)

[POJ 2486] Apple Tree(树型dp) Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 8981   Accepted: 2990 Description Wshxzt is a lovely girl. She likes apple very much. One day HX takes her to an apple tree. There are N nodes in the tree. Each

hdu 1754 splay tree伸展树 初战(单点更新,区间属性查询)

题意:与区间查询点更新,点有20W个,询问区间的最大值.曾经用线段树,1000+ms,今天的伸展树,890没ms,差不多. 第一次学习伸展树,一共花了2个单位时间,感觉伸展树真很有用,也很好玩.现在只学了一点点.切个点更新试试. 大致思路:用编号(数组)作为树的键值建树,每插一个数,沿路节点更新最大值(每个结点有一个附加信息标记以之为子树的树所有点的最大值).所以,查询时[i,j],只要把i-1伸展到树根,把j+1伸展到I-1下面,那么j+1的左子树就是要的区间了!查该子树根值信息即可(特判端点

页面设计--Tree目录树

Tree目录树控件属性: 根据数据集合来配置相应的信息 加载模式有自动加载.自定加载 web中显示效果图: