二叉树的遍历(递归思想):
采用递归的方式遍历二叉树,主要理解递归的思想,就例如拿前序遍历来理解,前序遍历,先遍历父结点,接着遍历左子树,然后遍历右子树,主要还要理解回溯的过程的思想。
代码如下:
#include <stdio.h>
#include <malloc.h>
#define maxsize 50
typedef char elemtype;
typedef struct node{
elemtype data;
struct node *lchild;//指向左孩子
struct node *rchild;//指向右孩子
}bnode;
//构造二叉树
void createtree(bnode *&b, char *str)
{
bnode *st[maxsize],*p ; //创建结构体类型的指针栈数组
int top = -1,k,j=0; //top是 数组下标,初始为-1;
char ch = str[j];
b = NULL; //空二叉树
while(ch != '\0')
{
switch(ch)
{
//下面3步是用来将数据入栈和设置k值的作用.
case '(': st[++top]=p;k=1;break;
case ')': top--;break;
case ',': k = 2;break;
default:
p = (bnode *)malloc(sizeof(bnode)); //创建一个结构体树节点指针类型
//创建完成之后,将数据赋值给创建的节点,并新创建的节点的左右指针初始化为空(NULL)
p ->data = ch;
p ->lchild =NULL;
p ->rchild =NULL;
if(b==NULL) //参数中传入的b是空,这一步用来构建根节点。
{
b = p;
}
else{
switch(k) //构建完根结点之后,将循环传入的字符元素data经过k判断是当作左孩子还是右孩子。
{
case 1:st[top]->lchild = p;break;
case 2:st[top]->rchild = p;break;
}
}
}
j++;
ch = str[j];
}
}
//输出二叉树
void disptree(bnode *b)
{
if(b!=NULL) //这里判断,如果递归的这棵树为空数,也就是没有任何元素的一棵树,就退出。
{
printf("%c",b->data);
if(b->lchild!=NULL || b->rchild!=NULL)//只要满足其中一个条件,就一定有子数
{
printf("("); //只要有孩子,就必须打印出 (
disptree(b->lchild); //先左子树递归
if(b->rchild!=NULL) printf(","); //如归要递归遍历到右子树,如果右子树为空,不用执行这一步
disptree(b->rchild);//在右子树递归
printf(")"); //只要有孩子,就必须打印出 )
}
}
}
void preorder(bnode *b)
{
if(b!=NULL)
{
printf("%c ", b->data);
preorder(b->lchild);
preorder(b->rchild);
}
}
void inorder(bnode *b)
{
if(b!=NULL)
{
inorder(b->lchild);
printf("%c ",b->data);
inorder(b->rchild);
}
}
void lastorder(bnode *b)
{
if(b!=NULL)
{
lastorder(b->lchild);
lastorder(b->rchild);
printf("%c ",b->data);
}
}
int main()
{
bnode *b,*p;// p用来接收查找的结点地址
printf("创建二叉树: ");
createtree(b,"A(B(D(,G)),C(E,F))");
disptree(b);
printf("\n前序遍历: ");
preorder(b);
printf("\n中序遍历: ");
inorder(b);
printf("\n后序遍历: ");
lastorder(b);
return 0;
}
程序运行如下: