数据结构(4)二叉树的基本操作——C语言代码实现

作为一个数据结构学习的新手,这篇文章也算是笔记了,请根据目录食用

目录

单链表的操作(C语言)

一、存储结构

二、前序递归建立二叉树

三、前序递归遍历二叉树

四、前序非递归遍历二叉树

五、中序非递归遍历二叉树

六、后序非递归遍历二叉树

七、层序遍历

八、层序遍历Pro(按层输出)(舍去,采用Pro++)

九、层序遍历Pro++(按层输出)

层序遍历Pro和层序遍历Pro++的对比反思

十、树的深度——递归实现

十一、结点数统计——递归实现

十二、度为0的结点的个数——递归实现

十三、度为1的结点的个数——递归实现

十四、度为2的结点的个数——递归实现

实现的总代码


单链表的操作(C语言)

一、存储结构

typedef struct Bitnode {
	Elemtype data;
	Bitnode *lchild, *rchild;
} Bitnode, *Bitree;

二、前序递归建立二叉树

void Creat(Bitree &T) {
	Elemtype n;
	scanf("%c", &n);
	if (n == '#')
		T = NULL;
	else {
		T = (Bitnode *)malloc(sizeof(Bitnode));
		T->data = n;
		T->lchild = NULL;
		T->rchild = NULL;
		Creat(T->lchild);
		Creat(T->rchild);
	}
}

三、前序递归遍历二叉树

void Inorder(Bitree T) {
	if (T) {
		printf("%c", T->data);//根
		Inorder(T->lchild);//左
		Inorder(T->rchild);//右
	}
}

中序递归和后序递归只需要调整语句的顺序即可,中序左根右,后序左右根

四、前序非递归遍历二叉树

void Fir_Inorder(Bitree T) {
	Bitree stack[100], p = T;    //用栈来实现
	int top = 0;
	while (p || top) {
		while (p) {
			stack[top] = p;
			top++;
			printf("%c", p->data);
			p = p->lchild;
		}
		top--;
		p = stack[top];
		p = p->rchild;
	}
}

【思路】由于前序的输出顺序为根左右,当遇到根的时候,将根压到栈里,并输出的data,再检查它的左孩子,当没有孩子的时候(p==NULL),指向栈顶,然后检查它的孩子;当有左孩子的时候(p ! = NULL),左孩子成为现在的根节点,重复上述步骤,直至所有结点都输出(栈空)。

五、中序非递归遍历二叉树

void Mid_Inorder(Bitree T) {
	Bitree stack[100], p = T;
	int top = 0;
	while (p || top) {
		while (p) {
			stack[top] = p;
			top++;
			p = p->lchild;
		}
		top--;
		p = stack[top];
		printf("%c", p->data);
		p = p->rchild;
	}
}

【思路】和前序非递归遍历的思路基本一致,只是输出顺序发生改变

六、后序非递归遍历二叉树

void Las_Inorder(Bitree T) {
	Bitree stack[100], p = T;
	int tag[100];
	int top = 0;
	while (p || top) {
		while (p) {
			top++;
			stack[top] = p;
			p = p->lchild;
			tag[top] = 1;
		}
		if (tag[top] == 1) {
			p = stack[top];
			tag[top] = 2;
			p = p->rchild;
		} else {
			p = stack[top];
			printf("%c", p->data);
			top--;
			p = NULL;
		}
	}
}

【思路】由于后序遍历的输出顺序为左右根,也就是说,需要检查并分别输出根节点的左右孩子后,才能输出根节点,也就是说在第三次访问根节点时才输出该根节点。

第一次访问,入栈,并设置标志(tag[top] = 1),访问该结点的左孩子;

第二次访问(该结点的左孩子为空),指针指向栈顶元素,并设置标志(tag[top] = 2),访问该结点的右孩子;

第三次访问(该结点的右孩子为空),指针指向栈顶元素,输出栈顶元素,栈顶指针减一。

        关键的是这个p = NULL,现在这个位置已经输出了(相当于左孩子或者右孩子为空了),需要让程序去处理前一个结点(前一个结点必然是被访问过一次或两次的),所以指针p指空,这样才可以进行第二次或第三次的访问。

七、层序遍历

void Level(Bitree T) {
	Bitree Q[100], p = T;   //用队列来实现
	int rear, front;
	rear = front = 0;
	rear++;
	Q[rear] = p;
	while (rear != front) {
		front++;
		p = Q[front];
		printf("%c", p->data);
        //每输出一个队头的结点,就要将它的左右孩子入队
		if (p->lchild) {
			rear++;
			Q[rear] = p->lchild;
		}
		if (p->rchild) {
			rear++;
	
评论 8
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值