04-树4 是否同一棵二叉搜索树
给定一个插入序列就可以唯一确定一棵二叉搜索树。然而,一棵给定的二叉搜索树却可以由多种不同的插入序列得到。例如分别按照序列{2, 1, 3}和{2, 3, 1}插入初始为空的二叉搜索树,都得到一样的结果。于是对于输入的各种插入序列,你需要判断它们是否能生成一样的二叉搜索树。
输入格式:
输入包含若干组测试数据。每组数据的第1行给出两个正整数NN (\le 10≤10)和LL,分别是每个序列插入元素的个数和需要检查的序列个数。第2行给出NN个以空格分隔的正整数,作为初始插入序列。最后LL行,每行给出NN个插入的元素,属于LL个需要检查的序列。
简单起见,我们保证每个插入序列都是1到NN的一个排列。当读到NN为0时,标志输入结束,这组数据不要处理。
输出格式:
对每一组需要检查的序列,如果其生成的二叉搜索树跟对应的初始序列生成的一样,输出“Yes”,否则输出“No”。
输入样例:
4 2
3 1 4 2
3 4 1 2
3 2 4 1
2 1
2 1
1 2
0
输出样例:
Yes
No
No
求解思路
两个序列是否对应相同搜索树的判别
1.分别建两棵搜索树的判别方法
2.不建树的判别方法
3. 建一棵树,再判别其他序列是否与该树一致
求解思路
1. 搜索树表示
2. 建搜索树T
3. 判别一序列是否与搜索树T一致
/*! * \file 04-树4 是否同一棵二叉搜索树.cpp * * \author ranjiewen * \date 三月 2017 * * */ //两个序列是否对应相同搜索树的判别 //1.分别建两棵搜索树的判别方法 //2.不建树的判别方法 //3. 建一棵树,再判别其他序列是否与该树一致 #include <stdio.h> #include <stdlib.h> typedef int Status; //函数类型 typedef int ElementType; typedef struct TreeNode* BSTree; struct TreeNode { ElementType Data; BSTree Left; BSTree Right; int Flag; //被访问为1,否则0 }; BSTree NewNode(ElementType data); BSTree Insert(BSTree T, ElementType data); BSTree MakeTree(int N); bool Check(BSTree T,ElementType data); int Judge(BSTree T); void ResetT(BSTree T); void FreeT(BSTree T); BSTree NewNode(ElementType data) { BSTree root = (BSTree)malloc(sizeof(struct TreeNode)); root->Data = data; root->Left = NULL; root->Right = NULL; root->Flag = 0; return root; } BSTree Insert(BSTree root, ElementType data) { if (root==NULL) { root = NewNode(data); } else { if (root->Data < data) { root->Right = Insert(root->Right, data); } else { root->Left = Insert(root->Left, data); } } return root; } BSTree MakeTree(int N) { BSTree T; ElementType data; scanf("%d", &data); T = NewNode(data); for (int i = 1; i < N; i++) { scanf("%d", &data); T = Insert(T, data); } return T; } //将另一棵树的结点依次在一颗二叉树上搜索,找到后标记;当搜索过程中有未被标记的结点,说明两棵树不一样 bool Check(BSTree T, ElementType data) { if (T->Flag) { if (data<T->Data) { return Check(T->Left, data); } else { return Check(T->Right, data); } } else { if (data==T->Data) { T->Flag = 1; return true; } else { return false; //结点不一致 } } } int Judge(BSTree T, int N) { ElementType data; int flag = 0; //0代表目前乃一致,1代表已经不一致 scanf("%d", &data); if (data!=T->Data) //判断根结点是否一致 { flag = 1; //不一致的情况下也要把后面的结点输入后才做判断 } else T->Flag = 1; for (int i = 1; i < N; i++) { scanf("%d", &data); if ((!flag)&&(!Check(T,data))) { flag = 1; } } if (flag) { return 0; } else return 1; } void ResetT(BSTree T) //清除T中各结点的flag标记 { if (T->Left) { ResetT(T->Left); } if (T->Right) { ResetT(T->Right); } T->Flag = 0; } void FreeT(BSTree T) //释放T的空间 { if (T->Left) { FreeT(T->Left); } if (T->Right) { FreeT(T->Right); } free(T); } int main() { int N; int L; BSTree T; scanf("%d", &N); while (N) //可以多次输入测试 { scanf("%d", &L); //需要检查的序列个数 T = MakeTree(N); //输入N个元素创建树 for (int i = 0; i < L;i++) //对每个序列操作 { if (Judge(T, N)) //依次输入N个元素,每个元素都进行标记判断 { printf("Yes\n"); } else { printf("No\n"); } ResetT(T); } FreeT(T); scanf("%d", &N); } }
C/C++基本语法学习
STL
C++ primer