二叉树的非递归遍历(C语言)

结合栈实现非递归遍历

先序遍历思想如下

步骤1:若当前结点有右子树,则将右子树结点压入栈,输出当前节点并指针往下走指向该节点的左子树。
步骤2:若左子树为空,则遍历右子树,重复步骤1,若右子树为空,弹栈输出指针指向该结点。

中序遍历思想如下

步骤1:若当前结点有左子树,则将当前结点压入栈,指针往下走指向该节点的左子树
	(相当于一直到最左下方),若无左子树了,则输出该结点。
步骤2:若当前结点有右子树,则指针指向该右子树,重复步骤1。
      若当前结点无右子树,则弹栈,输出栈顶元素,并让指针回退到栈顶元素对应的结点。
      若栈为空,则表示遍历结束。

后序遍历思想如下

步骤1:左子树不为空,将该结点压入栈,遍历左子树
步骤2:左子树为空则输出,在弹栈判断上一级节点右子树为空,则输出该结点,继续弹栈判断
	若不为空,则将该结点获取该节点的右子树,并把该结点再次压入栈,遍历右子树。
  • 单看理论比较难理解,读者可自行验证一下思想,更好理解。
  • 注意:本文未讲述栈模型,读者需有栈的基础知识

先序非递归代码

void unpre_order(BiTNode t)
{
	LinkStack *top;
	top = LinkStack_Create();;
	while(t != NULL || !isempty_linkstack(top)){
		if(t!=NULL){
			printf("%c",t->data);
			if(t->rchild != NULL);
				LinkStack_Push(t->rchild, &top);
			t = t->lchild;
		}else
			t = LinkStack_pop(&top);
	}
}

中序非递归代码

#include <stdio.h>
#include <string.h>
#include "linkstack.h"

//二叉链
struct BiTNode
{
	int data;
	struct BiTNode *lchild,*rchild;
};

typedef struct BiTNode BiTNode;
typedef struct BiTNode *BiTree;

BiTNode *goLeft(BiTNode *T, LinkStack *s)
{
	if(T == NULL){
		return NULL;
	}
	while(T->lchild != NULL){
		LinkStack_Push(s,T);
		T = T->lchild;
	}
	return T;
}
// 非递归中序
void Inorder2(BiTNode *T)
{
	BiTNode *t = NULL;
	LinkStack *s;
	s = LinkStack_Create();
	t = goLeft(T,s);
	while(t){
		printf("%d",t->data);
		//若t有右子树,重复步骤1
		if(t->rchild != NULL){
			t = goLeft(t->rchild,s);
		}
		//若t没有右子树,根据栈顶指示回退
		else if(t->rchild == NULL){
			t = LinkStack_Top(s);
			LinkStack_pop(s);
		}
		//若t没有右子树,并且栈为空
		else{
			t = NULL;
		}
	}
}

void inOrder(BiTNode *root)
{
	if(root == NULL){
		return ;
	}
	
	//遍历左子树
	inOrder(root->lchild);
	
	//打印根结点
	printf("%d\n",root->data);
	
	//遍历右子树
	inOrder(root->rchild);
}

int main(void)
{
	BiTNode t1,t2,t3,t4,t5;
	memset(&t1,0,sizeof(BiTNode));
	memset(&t2,0,sizeof(BiTNode));
	memset(&t3,0,sizeof(BiTNode));
	memset(&t4,0,sizeof(BiTNode));
	memset(&t5,0,sizeof(BiTNode));
	t1.data = 1;
	t2.data = 2;
	t3.data = 3;
	t4.data = 4;
	t4.data = 5;
	//建立关系
	t1.lchild = &t2;
	t1.rchild = &t3;
	t2.lchild = &t4;
	t3.lchild = &t5;

	//递归遍历
	printf("inOrder\n");
	inOrder(&t1);
	//非递归遍历
	printf("非递归\n");
	inOrder2(&t1);
	return 0;
}
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值