二叉树的非递归遍历
前言
二叉树的非递归遍历,对二叉树进行先序和中序遍历
一、树和队列的结构和初始化
typedef struct TreeNode //树的结构
{
char data; //数据域char类型
struct TreeNode* Lchild; //左孩子
struct TreeNode* Rchild; //右孩子
}TreeNode;
typedef struct stackNode //队列的结构
{
TreeNode* data; //data使用指针更好指向树的节点
struct stackNode* next; //next下一指针域
}stackNode;
void creatTree(TreeNode** node, char* data, int* index)
{
char temp;
temp = data[*index];
*index += 1;
if (temp == '#')
{
*node = NULL;
}
else
{
*node = (TreeNode*)malloc(sizeof(TreeNode));
(*node)->data = temp;
creatTree(&((*node)->Lchild), data, index);
creatTree(&((*node)->Rchild), data, index);
}
}
stackNode* initStack(void)
{
stackNode* stack = (stackNode*)malloc(sizeof(stackNode)); //开辟对stack空间
stack->data = NULL; //data指向的节点为NULL
stack->next = NULL; //next下一指针域也是nULL
return stack;
}
二、遍历
1.进出栈,并判断是否栈空
代码如下(示例):
void push(TreeNode* treedata, stackNode* stack)
{
stackNode* node = (stackNode*)malloc(sizeof(stackNode)); //开创一个node节点
node->data = treedata; //队列node的data指针指向树的节点
node->next = stack->next; //node的next指向stack的next
stack->next = node; //stack的next指向node
}
int isEmplt(stackNode* stack)
{
if (stack->next == NULL)
{
return 1;
}
else
{
return 0;
}
}
stackNode* pop(stackNode* stack)
{
if (isEmplt(stack))
{
return NULL;
}
else
{
stackNode* node = stack->next; //进栈前判断不为空,创建node,node指向stack的next
stack->next = node->next; //stack的next指向node的next,即指向node的next的next
return node;
}
}
2.前序遍历
代码如下(示例):
void PreOrder(TreeNode* tree) //前序遍历
{
TreeNode* node = tree; //创建node保存tree
stackNode* stack = initStack(); //初始化一个队列·
while (node || !isEmplt(stack)) //判断条件为node不为空,stack不为空
{
if (node)
{
printf("%c", node->data); //打印当前的node的数据域
push(node,stack); //进栈
node = node->Lchild; //node指向node的左孩子
}
else
{
node = pop(stack)->data; //如果node为空的话就出栈,回到上一个根节点
node = node->Rchild; //并node指向node的右孩子
}
}
}
3.中序遍历
代码如下(示例):
void inOrder(TreeNode* tree) //中序遍历
{
TreeNode* node = tree; //创建node保存tree
stackNode* stack = initStack(); //初始化一个队列·
while (node || !isEmplt(stack)) //判断条件为node不为空,stack不为空
{
if (node)
{
push(node, stack); //进栈
node = node->Lchild; //node指向node的左孩子
}
else
{
node = pop(stack)->data; //如果node为空的话就出栈,回到上一个根节点
printf("%c", node->data); //打印当前的node的数据域
node = node->Rchild; //并node指向node的右孩子
}
}
}
4.测试代码
代码如下(示例):
#include <stdio.h>
#include <stdlib.h>
typedef struct TreeNode //树的结构
{
char data; //数据域char类型
struct TreeNode* Lchild; //左孩子
struct TreeNode* Rchild; //右孩子
}TreeNode;
typedef struct stackNode //队列的结构
{
TreeNode* data; //data使用指针更好指向树的节点
struct stackNode* next; //next下一指针域
}stackNode;
void creatTree(TreeNode** node, char* data, int* index)
{
char temp;
temp = data[*index];
*index += 1;
if (temp == '#')
{
*node = NULL;
}
else
{
*node = (TreeNode*)malloc(sizeof(TreeNode));
(*node)->data = temp;
creatTree(&((*node)->Lchild), data, index);
creatTree(&((*node)->Rchild), data, index);
}
}
stackNode* initStack(void)
{
stackNode* stack = (stackNode*)malloc(sizeof(stackNode)); //开辟对stack空间
stack->data = NULL; //data指向的节点为NULL
stack->next = NULL; //next下一指针域也是nULL
return stack;
}
void push(TreeNode* treedata, stackNode* stack)
{
stackNode* node = (stackNode*)malloc(sizeof(stackNode)); //开创一个node节点
node->data = treedata; //队列node的data指针指向树的节点
node->next = stack->next; //node的next指向stack的next
stack->next = node; //stack的next指向node
}
int isEmplt(stackNode* stack)
{
if (stack->next == NULL)
{
return 1;
}
else
{
return 0;
}
}
stackNode* pop(stackNode* stack)
{
if (isEmplt(stack))
{
return NULL;
}
else
{
stackNode* node = stack->next; //进栈前判断不为空,创建node,node指向stack的next
stack->next = node->next; //stack的next指向node的next,即指向node的next的next
return node;
}
}
void PreOrder(TreeNode* tree) //前序遍历
{
TreeNode* node = tree; //创建node保存tree
stackNode* stack = initStack(); //初始化一个队列·
while (node || !isEmplt(stack)) //判断条件为node不为空,stack不为空
{
if (node)
{
printf("%c", node->data); //打印当前的node的数据域
push(node,stack); //进栈
node = node->Lchild; //node指向node的左孩子
}
else
{
node = pop(stack)->data; //如果node为空的话就出栈,回到上一个根节点
node = node->Rchild; //并node指向node的右孩子
}
}
}
void inOrder(TreeNode* tree) //中序遍历
{
TreeNode* node = tree; //创建node保存tree
stackNode* stack = initStack(); //初始化一个队列·
while (node || !isEmplt(stack)) //判断条件为node不为空,stack不为空
{
if (node)
{
push(node, stack); //进栈
node = node->Lchild; //node指向node的左孩子
}
else
{
node = pop(stack)->data; //如果node为空的话就出栈,回到上一个根节点
printf("%c", node->data); //打印当前的node的数据域
node = node->Rchild; //并node指向node的右孩子
}
}
}
void main(void)
{
char data[] = "ABD##E##CF##G##";
int index = 0;
TreeNode* tree;
creatTree(&tree,data,&index);
PreOrder(tree);
printf("\n");
inOrder(tree);
printf("\n");
}
总结
上述若有错位,麻烦请指出,谢谢啦。