程序员日记三号——二叉树

#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#define MAX  100


typedef char DataType;
typedef struct  Node
{
	DataType data;
	struct Node *Lchild,*Rchild;
}BiTNode,*BiTree;
typedef struct 
{
	BiTree data[MAX];
	int rear,front;
}SeQueue;
typedef struct
{
	BiTree data[MAX];
	int top;
}SeqStack;

int Count=0;
int depth=0;

void CreateBiTree(BiTree *root);//建立二叉树;
void Destory(BiTree *root);//销毁二叉树;
void TreeDepth(BiTree root,int h);//求树的高度;
BiTree Parent(BiTree root ,DataType current);//求二叉树的双亲结点;
BiTree LeftChild(BiTree root,DataType x);//求左孩子结点;
BiTree RightChild(BiTree root,DataType x);//求右孩子结点;
void PreOrder(BiTree root);//先序遍历操作;
void InOrder(BiTree root);//中序遍历操作;
void PostOrder(BiTree root);//后序遍历操作;
void LevelOrder(BiTree root);//层次遍历操作;
void PreOrderCount(BiTree root);//先序遍历统计叶子结点的结点数;
void InOrderPrint(BiTree root);//中序遍历输出叶子结点;
void PrintTree(BiTree root,int h);//按树状打印二叉树;


/*建立并初始化栈*/
SeqStack * InitStack()
{
	SeqStack *s;
	s=(SeqStack *)malloc(sizeof(SeqStack));
	s->top=-1;
	return s;
}
/*判空栈*/
int IsEmpty(SeqStack *s)
{
	if(s->top==-1)return 1;
	else return 0;
}
/*入栈*/
int Push(SeqStack *s,BiTree x)
{
	if(s->top==MAX-1)  return 0;
	else{
		s->top++;
		s->data[s->top]=x;
		return 1;
	}
}
/*出栈*/
int Pop(SeqStack *s,BiTree *x)
{
    if(IsEmpty(s))  return 0;
	else{
         *x=s->data[s->top];
		 s->top--;
		 return 1;
	}
}
/*取栈顶元素*/
void Top(SeqStack *s,BiTree *x)
{
	if(IsEmpty(s))
		return ;
	else
		*x=s->data[s->top];
}
SeQueue * InitQueue()//初始化队列;
{
   SeQueue *q;
   q=(SeQueue *)malloc(sizeof(SeQueue));
   q->front=q->rear=0;
   return q;
}
int  EmptyQueue(SeQueue *q)//判空队;
{
	if(q==NULL||q->rear==0)
		return 0;
	else return 1;
}
void EnterQueue(SeQueue *q,BiTree x)//入队;
{
	if(q->rear==0)
	{
		q->front=1;
		q->rear++;
	}
	else   q->rear++;
	q->data[q->rear]=x;
}
void DeleteQueue(SeQueue *q,BiTree *p)//出队;
{
	int i;
	if(EmptyQueue(q))
	{
     	*p=q->data[q->front];
     	for(i=1;i<=q->rear;i++)
		{
		    q->data[i]=q->data[i+1];
		}
	    q->rear--;
	}
	else return;
}
Visit(DataType x)
{
	printf("%c",x);
}
void Initiate(BiTree root)    //初始化二叉树;
{
	root=NULL;
}
void CreateBiTree(BiTree *root)//扩展先序遍历序列建立二叉树;
{
	char ch[2];
	scanf("%1s",&ch[0]);
	if(strcmp(ch,"#")==0)  *root=NULL;
	else
		{
	    	*root=(BiTNode *)malloc(sizeof(BiTNode));
			(*root)->data=ch[0];
    		CreateBiTree(&((*root)->Lchild));
			CreateBiTree(&((*root)->Rchild));
		}
}
void Destory(BiTree *root)//销毁二叉树;
{
	if(*root==NULL)  return ;
	Destory(&((*root)->Lchild));
	Destory(&((*root)->Rchild));
	free(*root);
    *root=NULL;
}
void PreOrder(BiTree root)//先序遍历操作;
{
	SeqStack *S=NULL;
	BiTree p;
   	S=InitStack();p=root;
	while(p!=NULL||!IsEmpty(S))
	{
		while(p!=NULL)
		{
              Visit(p->data );
			  Push(S,p);
			  p=p->Lchild;
		}
			  if(!IsEmpty(S))
			  {Pop(S,&p);p=p->Rchild;}
	}
}
void InOrder(BiTree root)//中序遍历操作;
{
	SeqStack *S=NULL;
	BiTree p;
	S=InitStack();p=root;
	while(p!=NULL||!IsEmpty(S))
	{
		while(p!=NULL)
		{
			  Push(S,p);
			  p=p->Lchild;
		}
		if(!IsEmpty(S))
		{Pop(S,&p);Visit(p->data );p=p->Rchild;}
	}
}
void PostOrder(BiTree root)//后序遍历操作;
{
    SeqStack *S=NULL;
	BiTree p,q;
	S=InitStack();p=root;q=NULL;
	while(p!=NULL||!IsEmpty(S))
	{
		while(p!=NULL)
		{
			  Push(S,p);
			  p=p->Lchild;
		}
			  if(!IsEmpty(S))
			  {
				  Top(S,&p);
				  if((p->Rchild==NULL)||(p->Rchild==q))
				  { Pop(S,&p);Visit(p->data );q=p;p=NULL;}
                  else p=p->Rchild;		
			  }
	}
}
void LevelOrder(BiTree root)//层次遍历;
{
	SeQueue *Q=NULL;
	BiTree p;
	Q=InitQueue();EnterQueue(Q,root);
	while(EmptyQueue(Q))
	{
		DeleteQueue(Q,&p);Visit(p->data);
		if(p->Lchild!=NULL)
			EnterQueue(Q,p->Lchild);
		if(p->Rchild!=NULL)
		    EnterQueue(Q,p->Rchild);
	}
}
void PreOrderCount(BiTree root)//先序遍历统计叶子结点数b;
{
	if(root)
	{
		if(root->Lchild==NULL&&root->Rchild==NULL)
		   Count++;
		PreOrderCount(root->Lchild);
		PreOrderCount(root->Rchild);
	}
}
void InOrderPrint(BiTree root)//中序遍历输出叶子结点;
{
	if(root)
	{
		InOrderPrint(root->Lchild);
		if(root->Lchild==NULL&&root->Rchild==NULL)
			printf("\t%c",root->data);
		InOrderPrint(root->Rchild);
	}
}
void TreeDepth(BiTree root,int h)//求二叉树的高度;
{
	if(root)
	{
		if(h>depth)  depth=h;
		TreeDepth(root->Lchild,h+1);
		TreeDepth(root->Rchild,h+1);
	}
}
BiTree Parent(BiTree root ,DataType current)//求二叉树的双亲结点;
{
	BiTree p=NULL;
	if(root==NULL)  return NULL;
	if(((root->Lchild!=NULL)&&(root->Lchild->data==current))||((root->Rchild!=NULL)&&(root->Rchild->data==current)))
		return root;
	p=Parent(root->Lchild,current);
	if(p!=NULL)  return p;
	else return(Parent(root->Rchild,current));
}
BiTree LeftChild(BiTree root ,DataType current)//求二叉树的左孩子结点;
{
	BiTree p;
	if(root==NULL)  return NULL;
	if(root->data==current)
		return root->Lchild;
	p=LeftChild(root->Lchild,current);
	if(p!=NULL)  return p;
	else return(LeftChild(root->Rchild,current));
}
BiTree RightChild(BiTree root ,DataType current)//求二叉树的右孩子结点;
{
	BiTree p;
	if(root==NULL)  return NULL;
	if(root->data==current)
		return root->Rchild;
	p=RightChild(root->Lchild,current);
	if(p!=NULL)  return p;
	else return(RightChild(root->Rchild,current));
}
void PrintTree(BiTree root,int h)//按树状打印二叉树;
{
	int i;
	if(root==NULL) return;
	else
	{
	PrintTree(root->Rchild,h+1);
	for(i=0;i<h;i++)  
		printf(" ");
	printf("%c\n",root->data);
	PrintTree(root->Lchild,h+1);
	}
}
void text_BiTree()
{
	int h=1;
	char cur[2]={0};
	BiTree current=NULL;
    BiTree root=NULL;
	Initiate(root);
	printf("\n请输入树的扩展的先序遍序列:");
	CreateBiTree(&root);
    TreeDepth(root, h);//求树的高度;
	printf("####1:树的高度为:%d\n",depth);
	printf("####2:二叉树的先序遍历序列:");
	PreOrder(root);//先序遍历操作;
	printf("\n");
	printf("####3:二叉树的中序遍历序列:");	
	InOrder(root);//中序遍历操作;
	printf("\n");
	printf("####4:二叉树的后序遍历序列:");
	PostOrder(root);//后序遍历操作
	printf("\n");
	printf("####5:二叉树的层次遍历序列:");
	LevelOrder(root);//层次遍历操作
	printf("\n");
	printf("####6:求二叉树的双亲结点\n      输入所求的结点为:");
	scanf("%s",cur);
    if(current=Parent(root ,cur[0]))//求二叉树的双亲结点;
	printf("      结点%c的双亲结点为:%c\n",cur[0],current->data);
	else printf("      出错!");
	printf("####7:求二叉树的左孩子结点\n      输入所求的结点为:");
	scanf("%s",cur);
    if(current=LeftChild(root,cur[0]))//求左孩子结点;
	printf("      结点%c的左孩子结点为:%c\n",cur[0],current->data);
	else printf("      不存在左孩子!\n");
	printf("####8:求二叉树的右孩子结点\n      输入所求的结点为:");
	scanf("%s",cur);
    if(current=RightChild(root ,cur[0]))//求右孩子结点;
	printf("      结点%c的右孩子结点为:%c\n",cur[0],current->data);
	else printf("      不存在右孩子!\n");
	PreOrderCount(root);//先序遍历统计叶子结点的结点数;
	printf("####9:二叉树共有叶子结点%d个\n",Count);
	printf("####10:二叉树的叶子结点有:");
    InOrderPrint(root);//中序遍历输出叶子结点;
	printf("\n");
	printf("####11:树状打印二叉树:\n");
	PrintTree(root,0);//按树状打印二叉树;
    Destory(&root);//销毁二叉树;
	if(root==NULL)printf("销毁二叉树成功!\n");
	else          printf("销毁二叉树失败!\n");
	
}
main()
{
	text_BiTree();
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
1. 什么是二叉树二叉树是一种树形结构,其中每个节点最多有两个子节点。一个节点的左子节点比该节点小,右子节点比该节点大。二叉树通常用于搜索和排序。 2. 二叉树的遍历方法有哪些? 二叉树的遍历方法包括前序遍历、中序遍历和后序遍历。前序遍历是从根节点开始遍历,先访问根节点,再访问左子树,最后访问右子树。中序遍历是从根节点开始遍历,先访问左子树,再访问根节点,最后访问右子树。后序遍历是从根节点开始遍历,先访问左子树,再访问右子树,最后访问根节点。 3. 二叉树的查找方法有哪些? 二叉树的查找方法包括递归查找和非递归查找。递归查找是从根节点开始查找,如果当前节点的值等于要查找的值,则返回当前节点。如果要查找的值比当前节点小,则继续在左子树中查找;如果要查找的值比当前节点大,则继续在右子树中查找。非递归查找可以使用栈或队列实现,从根节点开始,每次将当前节点的左右子节点入栈/队列,直到找到要查找的值或者栈/队列为空。 4. 二叉树的插入与删除操作如何实现? 二叉树的插入操作是将要插入的节点与当前节点的值进行比较,如果小于当前节点的值,则继续在左子树中插入;如果大于当前节点的值,则继续在右子树中插入。当找到一个空节点时,就将要插入的节点作为该空节点的子节点。删除操作需要分为三种情况:删除叶子节点、删除只有一个子节点的节点和删除有两个子节点的节点。删除叶子节点很简单,只需要将其父节点的对应子节点置为空即可。删除只有一个子节点的节点,需要将其子节点替换为该节点的位置。删除有两个子节点的节点,则可以找到该节点的后继节点(即右子树中最小的节点),将其替换为该节点,然后删除后继节点。 5. 什么是平衡二叉树? 平衡二叉树是一种特殊的二叉树,它保证左右子树的高度差不超过1。这种平衡可以确保二叉树的查找、插入和删除操作的时间复杂度都是O(logn)。常见的平衡二叉树包括红黑树和AVL树。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值