第三次编程作业

来源:互联网 发布:最近网络流行歌曲2017 编辑:程序博客网 时间:2024/04/29 22:34
03-树1 树的同构   (25分)


给定两棵树T1和T2。如果T1可以通过若干次左右孩子互换就变成T2,则我们称两棵树是“同构”的。例如图1给出的两棵树就是同构的,因为我们把其中一棵树的结点A、B、G的左右孩子互换后,就得到另外一棵树。而图2就不是同构的。


图1


图2

现给定两棵树,请你判断它们是否是同构的。

输入格式:

输入给出2棵二叉树树的信息。对于每棵树,首先在一行中给出一个非负整数NNN (≤10\le 1010),即该树的结点数(此时假设结点从0到N−1N-1N1编号);随后NNN行,第iii行对应编号第iii个结点,给出该结点中存储的1个英文大写字母、其左孩子结点的编号、右孩子结点的编号。如果孩子结点为空,则在相应位置上给出“-”。给出的数据间用一个空格分隔。注意:题目保证每个结点中存储的字母是不同的。

输出格式:

如果两棵树是同构的,输出“Yes”,否则输出“No”。

输入样例1(对应图1):

8A 1 2B 3 4C 5 -D - -E 6 -G 7 -F - -H - -8G - 4B 7 6F - -A 5 1H - -C 0 -D - -E 2 -

输出样例1:

Yes

输入样例2(对应图2):

8B 5 7F - -A 0 3C 6 -H - -D - -G 4 -E 1 -8D 6 -B 5 -E - -H - -C 0 2G - 3F - -A 1 4

输出样例2:

No


#include <stdio.h>#define Tree int#define Null -1#define MAXSIZE 10//结构数组 struct Node{char Element;Tree Left;Tree Right;}T1[MAXSIZE], T2[MAXSIZE];Tree BuildTree(struct Node TreeNode[]){int N, i;char ch, cl, cr;scanf("%d", &N);ch = getchar();int Check[N];for(i = 0; i < N; i++)Check[i] = 0;//处理左右子树for(i = 0; i < N; i++){scanf("%c %c %c", &TreeNode[i].Element, &cl, &cr);ch = getchar();if(cl != '-'){TreeNode[i].Left = cl - '0';Check[TreeNode[i].Left] = 1;}elseTreeNode[i].Left = Null;if(cr != '-'){TreeNode[i].Right = cr - '0';Check[TreeNode[i].Right] = 1;}elseTreeNode[i].Right = Null;}//无结点指向的结点则为 根结点 for(i = 0; i < N; i++)if(Check[i] == 0)break;/* test;printf("\n");for(i = 0; i < N; i++){printf("%d   ",Check[i]);printf("%c %d %d\n", TreeNode[i].Element, TreeNode[i].Left, TreeNode[i].Right);}printf("\n");*/return i;} //该函数只在此题MAXSIZE中有效,不能扩展到N int Judge(Tree R1, Tree R2){//两树都为空 if(R1 == Null && R2 == Null)return 1;//空树和非空树if((R1 == Null && R2 != Null) || (R1 != Null && R2 == Null))return 0;//两树的根节点不一样if(T1[R1].Element != T2[R2].Element)return 0;//若过两树的左子树都空,判断右子树是否一样if(T1[R1].Left == Null && T2[R2].Left == Null)return Judge(T1[R1].Right, T2[R2].Right);//若两树的左子树不空,并且左子树的结点元素都一样,判断左右子树是否一样if((T1[R1].Left != Null && T2[R2].Left != Null) && (T1[T1[R1].Left].Element == T2[T2[R2].Left].Element))return Judge(T1[R1].Left, T2[R2].Left) && Judge(T1[R1].Right, T2[R2].Right);else//否则 判断两树是否同构 return Judge(T1[R1].Left, T2[R2].Right) && Judge(T1[R1].Right, T2[R2].Left);}int main(){Tree Root1, Root2;Root1 = BuildTree(T1);Root2 = BuildTree(T2);if(Judge(Root1, Root2))printf("Yes");elseprintf("No");return 0;}



03-树2 List Leaves   (25分)


Given a tree, you are supposed to list all the leaves in the order of top down, and left to right.

Input Specification:

Each input file contains one test case. For each case, the first line gives a positive integerNNN (≤10\le 1010) which is the total number of nodes in the tree -- and hence the nodes are numbered from 0 toN−1N-1N1. Then NNN lines follow, each corresponds to a node, and gives the indices of the left and right children of the node. If the child does not exist, a "-" will be put at the position. Any pair of children are separated by a space.

Output Specification:

For each test case, print in one line all the leaves' indices in the order of top down, and left to right. There must be exactly one space between any adjacent numbers, and no extra space at the end of the line.

Sample Input:

81 -- -0 -2 7- -- -5 -4 6

Sample Output:

4 1 5


#include <stdio.h>#include <stdlib.h>#define MAXSIZE 10#define ElementType int #define Tree int #define Null -1//结构数组存结点的数据 typedef struct Node *PtrToNode;struct Node{ElementType Element;Tree Left;Tree Right;struct Node *Next;}TreeArray[MAXSIZE];//队列的头尾指针,指向结点 typedef struct QNode *Queue;struct QNode{PtrToNode Front;PtrToNode Rear;};Tree BuildTree(int N){int i;char ch, cl, cr;int Check[N];//Check数组 当结点指向i,则i不是根结点 for(i = 0; i < N; i++)Check[i] = 0;for(i = 0; i < N; i++){scanf("%c %c", &cl, &cr);ch = getchar();//有字符 读取回车 TreeArray[i].Element = i;//按给定的顺序依次录入 //处理左子树 if(cl != '-'){TreeArray[i].Left = cl - '0';Check[TreeArray[i].Left] = 1;}elseTreeArray[i].Left = Null;//处理右子树 if(cr != '-'){TreeArray[i].Right = cr - '0';Check[TreeArray[i].Right] = -1;}elseTreeArray[i].Right = Null;}//test !!!//for(i = 0; i < N; i++)//printf("%d %d %d\n", TreeArray[i].Element, TreeArray[i].Left, TreeArray[i].Right);//找出根结点 for(i = 0; i < N; i++)if(Check[i] == 0)break;return i;}Queue CreateQueue(Tree Root){Queue Q = (Queue)malloc(sizeof(struct QNode));//创建队列,指向根节点 Q->Front = Q->Rear = &TreeArray[Root];return Q;}void PrintLeave(Queue Q, int N){int i;//最后一个节点肯定是树叶,单独写,可处理最后的空格 for(i = 1; i < N; i++){//如果节点没有子树,则为树叶 if(Q->Front->Left == -1 && Q->Front->Right == -1)printf("%d ", Q->Front->Element);//如果有左子树,加入队列,尾指针后挪if(Q->Front->Left != -1){Q->Rear->Next = &TreeArray[Q->Front->Left];Q->Rear = Q->Rear->Next;}if(Q->Front->Right != -1){Q->Rear->Next = &TreeArray[Q->Front->Right];Q->Rear = Q->Rear->Next;}//遍历左右子树后,首指针后挪 Q->Front = Q->Front->Next;}printf("%d", Q->Front->Element);}int main(){int N;char ch;scanf("%d", &N);ch = getchar();Tree Root;Queue Q;Root = BuildTree(N);Q = CreateQueue(Root);PrintLeave(Q, N);return 0;} 


0 0