二叉树的前、中、后序、层序遍历 非递归 测试:ABC##DE#G##F###

/*
*二叉树的前、中、后序、层序遍历 非递归  测试:ABC##DE#G##F###
*/
#include<stdio.h>
#include<stdlib.h>

#define MAX_SIZE 100

typedef struct BiTNode
{
	char info;
	struct BiTNode *lchild;
	struct BiTNode *rchild;
}*BiTree;

typedef struct SeqStack
{
	BiTree s[MAX_SIZE];
	int t;
}*PSeqStack;

typedef struct QNode
{
	BiTree info;
	struct QNode *link;
}QNode,*QueuePtr;

typedef struct LinkQueue
{
	QueuePtr f;
	QueuePtr r;
}*PLinkQueue;

PSeqStack createEmptyStack_seq(void)
{
	PSeqStack p_stack;

	p_stack=(PSeqStack)malloc(sizeof(struct SeqStack));

	if(NULL==p_stack)
	{
		printf("\tout of space!\n");
		exit(-1);
	}
	else
	{
		p_stack->t=-1;	//以满堆栈的方式存储
	}

	return p_stack;
}
bool isEmptyStack_seq(PSeqStack p_stack)
{
	return p_stack->t==-1;
}
void push_seq(PSeqStack p_stack,BiTree bt)
{
	if(p_stack->t>=MAX_SIZE-1)
	{
		printf("\tOverflow\n");
		exit(-1);
	}
	++p_stack->t;

	p_stack->s[p_stack->t]=bt;
}
void pop_seq(PSeqStack p_stack)
{
	if(p_stack->t==-1)
	{
		printf("\tUnderflow\n");
		exit(-1);
	}
	--p_stack->t;
}
BiTree top_seq(PSeqStack p_stack)
{
	if(isEmptyStack_seq(p_stack))
	{
		printf("\tEmpty Stack\n");
	}
	return p_stack->s[p_stack->t];
}
PLinkQueue createEmptyQueue_link(void)
{
	PLinkQueue p_queue;

	p_queue=(PLinkQueue)malloc(sizeof(struct LinkQueue));
	if(NULL!=p_queue)
	{
		p_queue->f=NULL;
		p_queue->r=NULL;
	}
	else
		printf("\tout of space!\n");

	return p_queue;
}
bool isEmptyQueue_link(PLinkQueue p_queue)
{
	return p_queue->f==NULL;
}
void enQueue_link(PLinkQueue p_queue,BiTree bt)
{
	QueuePtr p;

	p=(QueuePtr )malloc(sizeof(struct QNode));

	if(NULL==p)
	{
		printf("\tout of space!\n");
		exit(-1);
	}
	else
	{
		p->info=bt;//将元素写入数据域
		p->link=NULL;//填写新节点的信息
		if(NULL==p_queue->f)
		{
			p_queue->f=p;
			p_queue->r=p;
		}
		else
		{
			p_queue->r->link=p;
			p_queue->r=p;
		}
	}
}
void deQueue_link(PLinkQueue p_queue)
{
	QueuePtr p;

	if(NULL==p_queue->f)
	{
		printf("\tEmptyQueue!\n");
		exit(-1);
	}
	else
	{
		p=p_queue->f;
		if(p_queue->f==p_queue->r)
			p_queue->r=NULL;
		p_queue->f=p->link;
		free(p);
	}
}
BiTree top_link(PLinkQueue p_queue)
{
	if(NULL==p_queue->f)
	{
		printf("\tEmptyQueue!\n");
		exit(-1);
	}
	else
		return p_queue->f->info;
}
BiTree createBiTree(BiTree bt)
{
	char ch;
	scanf("%c",&ch);
	//ch=getchar();

	if('#'==ch)
	{
		bt=NULL;
	}
	else
	{
		bt=(BiTree)malloc(sizeof(struct BiTNode));

		if(NULL==bt)
		{
			exit(-1);
		}
		bt->info=ch;		//生成根结点
		bt->lchild=createBiTree(bt->lchild);//构造左右子树
		bt->rchild=createBiTree(bt->rchild);
	}
	return bt;
}
BiTree leftChild(BiTree p)
{
	if(NULL==p)
	{
		return NULL;
	}
	return p->lchild;
}
BiTree rightChild(BiTree p)
{
	if(NULL==p)
	{
		return NULL;
	}
	return p->rchild;
}
void PreOrder(BiTree bt)
{
	PSeqStack p_stack;
	BiTree c;

	if(NULL==bt)
	{
		return ;
	}

	p_stack=createEmptyStack_seq();
	push_seq(p_stack,bt);

	while(!isEmptyStack_seq(p_stack))//栈不空,取栈顶,出栈
	{
		c=top_seq(p_stack);
		pop_seq(p_stack);

		if(NULL!=c)
		{
			printf("%c ",c->info);
			push_seq(p_stack,c->rchild);
			push_seq(p_stack,c->lchild);
		}
	}

}

void InOrder(BiTree bt)
{
	PSeqStack p_stack;

	p_stack=createEmptyStack_seq();

	BiTree c=bt;

	if(NULL==c)
	{
		return ;
	}
	do
	{
		while(NULL!=c)//二叉树不为空,延其左子树前进,当左子树为空,弹出栈顶元素
		{
			push_seq(p_stack,c);
			c=c->lchild;
		}
		c=top_seq(p_stack);//根指针退栈,访问根节点,遍历右子树
		pop_seq(p_stack);
		printf("%c ",c->info);
		c=c->rchild;
	}while(NULL!=c||!isEmptyStack_seq(p_stack));
}

void PostOrder(BiTree bt)
{
	PSeqStack p_stack;
	BiTree pre,p=bt;

	p_stack=createEmptyStack_seq();
	while(NULL!=p||!isEmptyStack_seq(p_stack))//反复地把遇到的二叉树进栈并进入它的左子树
	{
		while(NULL!=p)
		{
			push_seq(p_stack,p);
			pre=rightChild(p);
			p=leftChild(p);
			if(NULL==p)
			{
				p=pre;
			}
		}
		p=top_seq(p_stack);
		pop_seq(p_stack);
		printf("%c ",p->info);//栈顶二叉树的根是应访问节点
		if(!isEmptyStack_seq(p_stack)&&leftChild(top_seq(p_stack))==p)//若栈不空,且从左子树退回来
		{
			p= rightChild(top_seq(p_stack));	//进入右子树遍历
		}
		else
			p=NULL;//从右子树回来,退到上一层处理,执行出栈
	}

}
void levelOrder(BiTree bt)
{
	BiTree c,cc;
	PLinkQueue p_queue;

	p_queue=createEmptyQueue_link();
	if(NULL==bt)//空二叉树返回
	{
		return ;
	}
	c=bt;
	enQueue_link(p_queue,c);//将二叉树送入队列
	while(!isEmptyQueue_link(p_queue))
	{
		c=top_link(p_queue);
		deQueue_link(p_queue);
		printf("%c ",c->info);//从队头取出二叉树并访问

		cc=leftChild(c);
		if(NULL!=cc)	//将左子树送入队列
			enQueue_link(p_queue,cc);
		cc=rightChild(c);
		if(NULL!=cc)	//将右子树送入队列
			enQueue_link(p_queue,cc);
	}

}
int depth(BiTree bt)
{
	int d1,d2;

	if(!bt)
		return 0;
	d1=depth(bt->lchild);
	d2=depth(bt->rchild);

	return (d1>d2?d1:d2)+1;
} 
int CountNode(BiTree bt)
{
	if(NULL==bt)
		return 0;
	 return 1+CountNode(bt->lchild)+CountNode(bt->rchild);  
}
int main()
{
	BiTree bt=NULL;
	//int depth=0;

	printf("please input the value of tree:\n");
	bt=createBiTree(bt);
	printf("\n\n");

	printf("Pre Order:\n");
	PreOrder(bt);
	printf("\n\n");

	printf("In Order:\n");
	InOrder(bt);
	printf("\n\n");

	printf("Post Order:\n");
	PostOrder(bt);
	printf("\n\n");

	printf("level Order:\n");
	levelOrder(bt);
	printf("\n\n");

	printf("The depth of BiTree:%d",depth(bt));
	printf("\n\n");

	printf("the number of BiTree nodes:%d",CountNode(bt));
	printf("\n\n");

	return 0;
}


 

  • 1
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
当然,二叉树的遍历有三种主要方式:先序遍历(根-左-右)、序遍历(左-根-右)和后序遍历(左-右-根)。非递归的层次遍历(也叫广度优先遍历,从上到下、从左到右)通常使用队列来辅助实现。 这里分别给出这些遍历的非递归算法代码: 1. 层序遍历(广度优先遍历): ```c #include <stdio.h> #include <stdlib.h> #include <queue> struct TreeNode { int val; struct TreeNode *left; struct TreeNode *right; }; void levelOrder(struct TreeNode* root) { if (root == NULL) return; // 使用队列存储每一层的节点 queue<struct TreeNode*> q; q.push(root); while (!q.empty()) { int size = q.size(); for (int i = 0; i < size; i++) { struct TreeNode* node = q.front(); q.pop(); printf("%d ", node->val); // 打印当节点值 if (node->left != NULL) q.push(node->left); if (node->right != NULL) q.push(node->right); } printf("\n"); // 换行表示新的一层 } } ``` 2. 先序遍历(递归和非递归两种方式,这里是非递归版本,使用栈): ```c void preorderNonRecursive(struct TreeNode* root) { if (root == NULL) return; stack<struct TreeNode*> s; s.push(root); while (!s.empty()) { struct TreeNode* node = s.top(); s.pop(); printf("%d ", node->val); // 打印当节点值 if (node->right != NULL) s.push(node->right); if (node->left != NULL) s.push(node->left); } } ``` 3. 序遍历(非递归,同样使用栈): ```c void inorderNonRecursive(struct TreeNode* root) { if (root == NULL) return; stack<struct TreeNode*> s; struct TreeNode* curr = root; while (curr != NULL || !s.empty()) { while (curr != NULL) { s.push(curr); curr = curr->left; } curr = s.top(); s.pop(); printf("%d ", curr->val); // 打印当节点值 curr = curr->right; } } ``` 4. 后序遍历(非递归,使用两个栈): ```c void postorderNonRecursive(struct TreeNode* root) { if (root == NULL) return; stack<struct TreeNode*> s1, s2; s1.push(root); while (!s1.empty()) { struct TreeNode* node = s1.top(); s1.pop(); s2.push(node); if (node->left != NULL) s1.push(node->left); if (node->right != NULL) s1.push(node->right); } while (!s2.empty()) { struct TreeNode* node = s2.top(); s2.pop(); printf("%d ", node->val); // 打印当节点值 } } ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值