13年大一第二学期学数据结构的时候写的了,今天发现草稿箱里面有这篇,就顺手发出来了。程序里面有二叉树先序遍历,后序遍历,中序遍历及其非递归遍历的方法,还有层次遍历跟查找某个节点的路径的方法,涉及到的数据结构有二叉树,栈跟队列。其实还有一些缺陷,有时间再去改正吧,不过对于学习理解还是不错的。
# include <stdio.h>
# include <stdlib.h>
# include <conio.h>
# define STACKSIZE 100
typedef char TElemType;
typedef struct BiTNode
{
TElemType data;
struct BiTNode *lchild;
struct BiTNode *rchild;
}*BiTree,BiTNode;
typedef BiTree SElemType;
typedef struct
{
SElemType data[STACKSIZE];
int top;
}SeqStack;
typedef BiTree QElemType;
typedef struct node
{
QElemType data;
struct node *next;
}QNode,*QNodeptr;
typedef struct
{
QNode *front;
QNode *rear;
}*LinkQueue,Queue;
/*对队列进行初始化操作*/
void InitQueue(LinkQueue *Q)
{
(*Q) = (LinkQueue)malloc(sizeof(Queue));
(*Q)->front = (QNode *)malloc(sizeof(QNode));
if(!(*Q)->front)
{
printf("Memory error!\n");
exit(0);
}
(*Q)->rear = (*Q)->front;
(*Q)->rear->next = NULL;
}
/*入队操作*/
void EnQueue(LinkQueue *Q,QElemType value)
{
QNode *temp;
temp = (QNodeptr)malloc(sizeof(QNode));
if(!temp)
{
printf("memroy error!\n");
exit(0);
}
temp->data = value;
temp->next = NULL;
(*Q)->rear->next = temp;
(*Q)->rear = temp;
}
/*出队操作*/
void DeQueue(LinkQueue *Q,QElemType *x)
{
QNode *temp;
/*
temp = (QNodeptr)malloc(sizeof(QNode));
if(!temp)
{
printf("memroy error!\n");
exit(0);
}
*/
temp = (*Q)->front->next;
*x = temp->data;
(*Q)->front->next = temp->next;
if((*Q)->rear==temp)
(*Q)->rear=(*Q)->front;
free(temp);
}
/*判断队列是否为空*/
int EmptyQueue(LinkQueue Q)
{
if(Q->front == Q->rear)
return 1;
else
return 0;
}
/*初始化一个栈*/
void InitStack(SeqStack *S)
{
S->top = 0;
}
/*将val入栈*/
int Push(SeqStack *S,SElemType val)
{
if(S->top >= STACKSIZE)
{
printf("栈已满,入栈失败!\n");
return 0;
}
S->data[S->top] = val;
S->top++;
}
/*对栈内元素进行输出*/
int Output(SeqStack S)
{
int i;
if(S.top == 0)
{
printf("未找到该节点!");
return 0;
}
else
{
printf("该节点的路径为:\n");
for(i = 0;i < S.top;i++)
{
printf("%c",S.data[i]->data);
if(i != S.top-1)
printf("->");
}
}
}
/*出栈操作,将出栈的值赋给x*/
int Pop(SeqStack *S,SElemType *x)
{
if(S->top == 0)
{
printf("栈为空,出栈失败!\n");
return 0;
}
S->top--;
*x = S->data[S->top];
}
/*判断栈是否为空*/
int StackEmpty(SeqStack S)
{
if(S.top==0)
return 1;
else
return 0;
}
/*得到栈顶元素*/
int GetTop(SeqStack S,SElemType *x)
{
if(S.top == 0)
{
printf("栈为空!\n");
return 0;
}
else
*x = S.data[S.top-1];
}
/*清空缓冲区*/
void flush()
{
while(getchar() != '\n');
}
/*初始化一个二叉树*/
void InitBiTree(BiTree *T)
{
*T = NULL;
}
/*递归先序创建一颗二叉树*/
void CreateBiTree(BiTree *T)
{
char ch;
printf("ch =");
scanf("%c",&ch);
flush();
if(ch == ' ')
*T=NULL;
else
{
*T = (BiTree)malloc(sizeof(BiTNode));
(*T)->data = ch;
CreateBiTree(&(*T)->lchild);
CreateBiTree(&(*T)->rchild);
}
}
/*非递归先序遍历二叉树*/
void PreTraverse(BiTree T)
{
SeqStack S;
InitStack(&S);
Push(&S,T);
while(!StackEmpty(S))
{
Pop(&S,&T);
printf("%c ",T->data);
if(T->rchild)
Push(&S,T->rchild);
if(T->lchild)
Push(&S,T->lchild);
}
}
/*先序递归遍历二叉树*/
void PreOrderTraverse(BiTree T)
{
if(T)
{
printf("%c ",T->data);
PreOrderTraverse(T->lchild);
PreOrderTraverse(T->rchild);
}
}
/*递归中序遍历二叉树*/
void InOrderTraverse(BiTree T)
{
if(T)
{
PreOrderTraverse(T->lchild);
printf("%c ",T->data);
PreOrderTraverse(T->rchild);
}
}
/*非递归中序输出*/
void InTraverse(BiTree T)
{
SeqStack S;
InitStack(&S);
while(T || !StackEmpty(S))
{
if(T)
{
Push(&S,T);
T = T->lchild;
}
else
{
Pop(&S,&T);
printf("%c ",T->data);
T = T->rchild;
}
}
}
/*递归后序遍历二叉树*/
void PostOrderTraverse(BiTree T)
{
if(T)
{
PreOrderTraverse(T->lchild);
PreOrderTraverse(T->rchild);
printf("%c ",T->data);
}
}
/*水平遍历一个二叉树*/
void LeverlOrderTraverse(BiTree T)
{
LinkQueue Q;
QElemType a;
if(T)
{
InitQueue(&Q);
EnQueue(&Q,T);
while(!EmptyQueue(Q))
{
DeQueue(&Q,&a);
printf("%c ",a->data);
if(a->lchild!=NULL)
EnQueue(&Q,a->lchild);
if(a->rchild!=NULL)
EnQueue (&Q,a->rchild);
}
}
}
/*查找节点的路径*/
SeqStack SearchPath(BiTree T,TElemType val)
{
SeqStack S;
InitStack(&S);
int flag = 0;
BiTree ht;
Push(&S,T);
while(!StackEmpty(S))
{
GetTop(S,&ht);
if(ht->data == val)
{
//printf("%c",ht->data);
return S;
break;
}
else if(flag == 0)
{
if(/*ht->data != val && */ht->lchild != NULL)
Push(&S,ht->lchild);
else
flag = 1;
}
else
{
if(ht->rchild != NULL)
{
Push(&S,ht->rchild);
flag = 0;
}
else
{
Pop(&S,&T);
while(!StackEmpty(S))
{
GetTop(S,&ht);
if(ht->rchild != T)
break;
Pop(&S,&T);
}
}
}
}
}
int Menu(BiTree T)
{
char i;
do
{
system("cls");
printf("******************************************************************\n");
printf("*\t\t请选择:\n*\n");
printf("*\t\t1.先序递归遍历二叉树\n");
printf("*\t\t2.先序非递归遍历二叉树\n");
printf("*\t\t3.中序递归遍历二叉树\n");
printf("*\t\t4.中序非递归遍历二叉树\n");
printf("*\t\t5.后序递归遍历二叉树\n");
printf("*\t\t6.层次遍历二叉树\n");
printf("*\t\t7.查找二叉树中某个节点的路径\n");
printf("*\t\t0.结束\n");
printf("******************************************************************\n");
printf("请输入你的选择:\n");
scanf("%c",&i);
flush();
if(i == '0')
{
printf("\t\t\t感谢使用!\n");
break;
}
else
switch(i)
{
case '1':
printf("先序递归遍历二叉树的结果为:\n");
PreOrderTraverse(T);
printf("\n请按回车键或者任意键继续!\n");
getch();
break;
case '2':
printf("先序非递归遍历二叉树的结果为:\n");
PreTraverse(T);
printf("\n请按回车键或者任意键继续!\n");
getch();
break;
case '3':
printf("中序递归遍历二叉树的结果为:\n");
InOrderTraverse(T);
printf("\n请按回车键或者任意键继续!\n");
getch();
break;
case '4':
printf("中序非递归遍历二叉树的结果为:\n");
InTraverse(T);
printf("\n请按回车键或者任意键继续!\n");
getch();
break;
case '5':
printf("后序递归遍历二叉树的结果为:\n");
PostOrderTraverse(T);
printf("\n请按回车键或者任意键继续!\n");
getch();
break;
case '6':
printf("层次遍历二叉树的结果为:\n");
LeverlOrderTraverse(T);
printf("\n请按回车键或者任意键继续!\n");
getch();
break;
case '7':
SeqStack S;
char ch;
InitStack(&S);
printf("请输入要查找的节点:\n");
scanf("%c",&ch);
flush();
S = SearchPath(T,ch);
Output(S);
printf("\n请按回车键或者任意键继续!\n");
getch();
break;
default:
printf("\007\t\t输入错误,请重新输入!\n");
printf("\n\t\t请按回车键或者任意键继续!\n");
getch();
}
}
while(i != '0');
}
int main()
{
BiTree T;
InitBiTree(&T);
printf("请先创建一个二叉树:\n");
CreateBiTree(&T);
Menu(T);
system("pause");
}