数据结构--实验二:二叉树的创建及遍历

一.实验目的
(1)熟练掌握二叉树的结构特征,以及各种存储结构的特点及适用范围。
(2)掌握在二叉链表存储结构中的常用遍历方法:先序递归遍历、中序递归遍历、后序递归遍历、中序遍历非递归算法;了解二叉树的层序遍历。
(3)了解二叉树遍历算法的简单应用。
二.实验内容
1.问题描述

已知二叉树,如图所示,基于图示二叉树编程实现以下算法:
(1) 创建二叉树,以先序次序输入二叉树序列创建二叉树;
(2) 采用先序遍历的递归算法遍历二叉树,并输出先序序列;
(3) 采用中序遍历的递归和非递归算法遍历二叉树,并输出中序序列;
(4) 采用后序遍历的递归算法遍历二叉树,并输出后序序列;
(5) 计算二叉树的高度并输出;
(6) 计算二叉树中所有结点个数并输出;
(7) 计算二叉树中叶子结点个数并输出。

2. 实验要求

(1)设计二叉树的链式存储结构;
(2)用先序创建的方式创建二叉树;
(3)每完成一个算法,及时输出结果,便于观察操作结果;
(4)设计测试用例,测试程序的正确性。
3. 测试用例
序号 输入 输出 说明
1 ABC@@DE@G@@F@@@ 先序遍历:ABCDEGF
中序遍历(递归):CBEGDFA
中序遍历(非递归):CBEGDFA
后序遍历:CGEFDBA
该二叉树的高度为: 5
该二叉树中所有结点个数为: 7
该二叉树中叶子结点个数为: 3
2 ABD@@EG@@@C@F@@ 先序遍历:ABDEGCF
中序遍历(递归):DBGEACF
中序遍历(非递归):DBGEACF
后序遍历:DGEBFCA
该二叉树的高度为: 4
该二叉树中所有结点个数为: 7
该二叉树中叶子结点个数为: 3
3 @ 空树

三.数据结构及相关函数说明

#include<stdio.h>
#include<stdlib.h>
#define MAXSIZE 100

typedef struct TNode * BinTree;   /* 二叉树类型 */
typedef char ElementType;
struct TNode{    /* 树结点定义 */ 
	ElementType Data;  /* 结点数据 */
	BinTree Left;   /* 指向左子树 */ 
	BinTree Right;   /* 指向右子树 */ 
}; 
typedef BinTree ElemType;
struct SNode{
	ElemType *Data;
	int Top;
	int Maxsize;
};
typedef struct SNode *Stack;

Stack CreatStack(){ 			//创建栈 
	Stack S;
	S=(Stack)malloc(sizeof(struct SNode));
	S->Top=-1;
	S->Maxsize=MAXSIZE;
	return S;
} 


bool IsEmpty(Stack S){  		//判断栈是否为空 
	if(S->Top==-1){
		return true;
	}
	else return false;
}

bool IsFull(Stack S,ElemType c){	//入栈 
	if(S->Top==(S->Maxsize-1)){
		return false;
	}
	else{
		S->Data[++S->Top]=c;
		return true;
	}
}


ElemType IsPop(Stack S){
		return S->Data[S->Top--];
}

//按先序次序输入二叉树中结点的值(一个字符),@表示空树,构造二叉链表表示二叉树T 
BinTree CreatBinTree()
{
		ElementType ch;
		BinTree T;
		scanf("%c",&ch);
		if(ch == '@')
		   T = NULL;
		else {
			T = (BinTree)malloc(sizeof(struct TNode));
			T->Data = ch;
			T->Left = CreatBinTree();
			T->Right = CreatBinTree();
		}
		return T;
} 

void PreorderTraversal(BinTree BT){  			//先序遍历 
	if(BT!=NULL){
		printf("%c",BT->Data);
		PreorderTraversal(BT->Left);
		PreorderTraversal(BT->Right);
	}
}

void InorderTraversal(BinTree BT){				//中序遍历 
	if(BT!=NULL){
		InorderTraversal(BT->Left);
		printf("%c",BT->Data);
		InorderTraversal(BT->Right);
	}
}

void PostorderTraversal(BinTree BT){				//后序遍历 
	if(BT!=NULL){
		PostorderTraversal(BT->Left);
		PostorderTraversal(BT->Right);
		printf("%c",BT->Data);
	}
}

void Inorder(BinTree BT){							//中序遍历非递归 
	Stack st;
	BinTree T=BT;
	st=CreatStack();
	while(T||!IsEmpty(st)){
		while(T){
			IsFull(st,T);
			T=T->Left;		
		}
		T=IsPop(st);
		printf("%c",T->Data);
		T=T->Right;
	}
	
}

int GetHeight(BinTree BT){							//计算二叉树的高度 
	if(BT){
		int tl=GetHeight(BT->Left);
		int tr=GetHeight(BT->Right);
		int t=tl>tr?tl+1:tr+1;
		return t;
	}
	else return 0;
}

int NodeCount(BinTree BT){							//计算结点总数 
	if(BT){
		return 1+NodeCount(BT->Left)+NodeCount(BT->Right);
	}
	else return 0;
}

int  PreOrderPrintLeaves(BinTree BT){				//计算叶节点 
	if(BT){
		if(BT->Left==NULL&&BT->Right==NULL){
			return 1+PreOrderPrintLeaves(BT->Left)+PreOrderPrintLeaves(BT->Right);
		}
		else return PreOrderPrintLeaves(BT->Left)+PreOrderPrintLeaves(BT->Right);
	}
	else return 0;

}

int main()
{
    BinTree BT;
    int height,count,leafnum;
    printf("请按先序次序输入树的结点,空树输入@: ");
    BT = CreatBinTree();
    
    if(BT == NULL){
    	printf("\n空树!\n"); 
	}else{
		printf("先序遍历的结果为: "); 
	    PreorderTraversal(BT);
	    printf("\n"); 
	    
	    printf("中序遍历的结果为(递归): "); 
	    InorderTraversal(BT);
	    printf("\n"); 
	    
	    printf("中序遍历的结果为(非递归): "); 
	    Inorder(BT);
	    printf("\n"); 
	    
	    printf("后序遍历的结果为: "); 
	    PostorderTraversal(BT);
	    printf("\n"); 
	    
	    height = GetHeight(BT);
	    printf("该二叉树的高度为: %d",height); 
	    printf("\n");
	    
	    count = NodeCount(BT);
	    printf("该二叉树中所有结点个数为: %d",count); 
	    printf("\n");
	    
	    leafnum = PreOrderPrintLeaves(BT) ;
	    printf("该二叉树中叶子结点个数为: %d",leafnum); 
	    printf("\n");
	} 
}
已标记关键词 清除标记
©️2020 CSDN 皮肤主题: 深蓝海洋 设计师:CSDN官方博客 返回首页