左神算法进阶班1_2判断两个树的结构是否相同


Promblem:
  给定两个二叉树T1和T2,返回T1的某个子树结构是否与T2的结构相等。

Solution:
  首相将两棵树进行序列化【切记加上分割符和空节点标记】,

  然后使用KMP算法进行两个字符串匹配,判断子树串是否属于原树串即可

Code:

  

 1 #pragma once
 2 #include <iostream>
 3 #include <string>
 4 
 5 using namespace std;
 6 
 7 struct Node
 8 {
 9     char c;
10     Node* lchild;
11     Node* rchild;
12     Node(char a) :c(a), lchild(nullptr), rchild(nullptr) {}
13 };
14 
15 void getSequence(string &str, Node* root)
16 {
17     if (root == nullptr)
18         str += "#_";
19     else
20     {
21         str = str + root->c + "_";
22         getSequence(str, root->lchild);
23         getSequence(str, root->rchild);
24     }
25 }
26 
27 void getIndex(int*& index, string str)
28 {
29     for (int i = 0, p = 0; i < str.length(); ++i)
30     {
31         if (0 == i)
32             index[0] = -1;
33         else if (1 == i)
34             index[i] = 0;
35         else
36         {
37             if (str[i - 1] == str[p])
38                 index[i] = ++p;
39             else if (p > 0)
40                 p = index[p];
41             else
42                 index[i] = 0;
43         }
44     }
45 }
46 
47 bool isSubTree(Node* root1, Node* root2)
48 {
49     string str1, str2;
50     str1 = str2 = "";
51     //序列化
52     getSequence(str1, root1);
53     getSequence(str2, root2);
54     //获取子树的前后缀长度
55     int* index = new int[str2.length()];
56     getIndex(index, str2);
57     
58     //使用KMP进行判断
59     int i, j;
60     i = j = 0;
61     while (i < str1.length() && j < str2.length())
62     {
63         if (str1[i] == str2[j])
64         {
65             ++i;
66             ++j;
67         }
68         else if (-1 == index[j])
69         {
70             j = 0;
71             ++i;
72         }
73         else
74             j = index[j];
75     }
76     delete[] index;
77     return (i <= str1.length() && j >= str2.length());
78 }
79 
80 void Test()
81 {
82     Node *root1, *root2;
83     root1 = new Node('5');
84 
85     root1->lchild = new Node('4');
86     root1->rchild = new Node('3');
87     root1->lchild->lchild = new Node('2');
88     root1->lchild->rchild = new Node('1');
89     root1->rchild->rchild = new Node('1');
90 
91     root2 = new Node('3');
92     root2->rchild = new Node('1');
93     cout << isSubTree(root1, root2) << endl;
94 
95     root2 = nullptr;
96     root2 = new Node('4');
97     root2->lchild = new Node('2');
98     cout << isSubTree(root1, root2) << endl;
99 }

 

上一篇:File Transfer


下一篇:131-19. 删除链表的倒数第N个节点