二叉树的先序中序后序实现(递归/非递归)

二叉树的先序,中序,后序实现(递归/非递归)

了解了二叉树的构造
知道如何遍历树才能满足查找的需求

这里介绍三种遍历:
先序遍历 根-》左-》右
中序遍历 左-》根-》右
后序遍历 左-》右-》根

typedef struct TreeNode * BinTree;
typedef BinTree Position;
typedef int ElementType;

struct TreeNode{
	ElementType d;
	BinTree Left;
	BinTree Right;
};

用递归的方式非常容易实现先序中序后序的遍历
先序–递归

void PreOrderTraversal(BinTree BT){
	if(BT){
		printf("%d",BT->d);
		PreOrderTraversal(BT->Left);
		PreOrderTraversal(BT->Right);
	}
}

中序–递归

void InOrderTraversal(BinTree BT){
	if(BT){
		InOrderTraversal(BT->Left);
		printf("%d",BT->d);
		InOrderTraversal(BT->Right);
	}
}

后序–递归

void PostOrderTraversal(BinTree BT){
	if(BT){
		PostOrderTraversal(BT->Left);
		PostOrderTraversal(BT->Right);
		printf("%d",BT->d);
	}
}

以上是通过递归实现
我们可以发现这种其实很好记
只要记住顺序,在上述口诀的根处打印即可~

然而
我们秉着生存之道还要了解非递归的实现
谁叫面试题考呢。。。

非递归–先序

void PreOrderTraversal(BinTree BT){
	BinTree T = BT;
	Stack s = CreateStack();
	while(T || !IsEmpty(s)){		//树不空或者栈不空 
		while(T){		
			printf("%d",T->d);			//树不空
			Push(T->d,s);
			T = T->Left;
		}
		if(!IsEmpty(s)){			//栈不空 
			T = Pop(s);
			T = T->Right;
		}
	} 
} 

非递归–中序

void InOrderTraversal(BinTree BT){
	BinTree T = BT;
	Stack s = CreateStack();
	while(T || !IsEmpty(s)){		//树不空或者栈不空 
		while(T){					//树不空
			Push(T->d,s);
			T = T->Left;
		}
		if(!IsEmpty(s)){			//栈不空 
			T = Pop(s);
			printf("%d",T->d);
			T = T->Right;
		}
	} 
} 

非递归–后序

void PostOrderTraversal(BinTree BT){
	BinTree T = BT,p = NULL;
	Stack s = CreateStack();
	while(T || !IsEmpty(s)){		//树不空或者栈不空 
		while(T){					//树不空
			Push(T->d,s);
			T = T->Left;
		}
		if(!IsEmpty(s)){			//栈不空 
			T = Pop(s);
		}
		if(T->Right == p || T->Right == NULL){
			printf("%d",T->d);
			p = T;
			T = NULL;
		}
		else{
			Push(T->d,s);
			T = T->Right;
		}
	} 
} 

这里我们可以通过观察
发现先序遍历和中序遍历的非递归代码很相近

其中的差别就是调整了printf的位置
中序遍历在Pop之后
而先序遍历在第一次访问也就是Push之前

所以要背也是很容易的
还是要在理解的基础上啦

而后序遍历时还要判断有无右子树
如果有右子树则仍要入栈,反之才能打印,
因为后序遍历的顺序是左-》右-》根

明天继续学习有关树的知识~
晚安啦~

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值