樹的總結(二)---非空二叉樹的高度和寬度

1.非空二叉樹的高度

     1.1非遞歸算法實現求解非空二叉樹的高度

 算法思想:採用層次遍歷的算法,設置變量level記錄當前結點所在的層數,設置變量last指向當前層的最右的結點,每次層次遍歷出隊的時候與last指針比較(front與last比較),若兩者相等,則層數加1,並讓last指向下一層的最右結點,直到遍歷完成。 level的值即爲二叉樹的高度。

int Btdepth(BTNode *T)
{
	if(T==NULL)
	   return 0;
	int front,rear;   //初始化層次遍歷需要的循環隊列 
	front=rear=-1;
	BTNode *Que[maxsize];
	int last=0,level=0;
	BTNode *p; 
	
	Que[++rear]=T;
	while(front<rear)      //隊列不空 
	{
		p=Que[++front];
		if(p->lchild!=NULL)
			Que[++rear]=p->lchild;
		if(p->rchild!=NULL)
			Que[++rear]=p->rchild;
		if(front==last)
		{
		   level++;
		   last=rear;
		}
	}
	return level;
}
 

    1.2遞歸算法求解非空二叉樹的高度

int getDepth(BTNode *T)
{
	int LD,RD;
	if(T==NULL)
	   return 0;
	else
	{
		LD=getDepth(T->lchild);
		RD=getDepth(T->rchild);
		return (LD>RD?LD:RD)+1; 
	}
}

 

2.求解非空二叉樹的寬度

算法思想:採用層次遍歷的方法求出所有結點的層次,並將所有結點和對應的層次放在一個隊列中。然後通過掃描隊列求出各層的結點總數,最大的層結點數即爲二叉樹的寬度。

int BtWidth(BTNode *T)
{
	BTNode *p;
	int k,max,i,n;
	Que Qu;
	Qu.front=Qu.rear=-1;  //隊列爲空
	Qu.rear++;
	Qu.data[Qu.rear]=T;   //根節點指針入隊 
	Qu.level[Qu.rear]=1;   //根節點的層次爲1
	while(Qu.front<Qu.rear)
	{
		Qu.front++;  //出隊
		p=Qu.data[Qu.front];  //出隊結點
		k=Qu.level[Qu.front];   //出隊結點層次
		if(p->lchild!=NULL)     //左孩子進隊 
		{
			Qu.rear++;
			Qu.data[Qu.rear]=p->lchild;
			Qu.level[Qu.rear]=k+1;
		 } 
		 if(p->rchild!=NULL)    //右孩子入隊 
		 {
		 	Qu.rear++;
		 	Qu.data[Qu.rear]=p->rchild;
		 	Qu.level[Qu.rear]=k+1;
		 }
	 }//while
	 max=0;i=0;     //max保存同一層最多的結點個數
	 k=1;
	 while(i<Qu.rear)
	 {
	 	n=0;
	 	while(i<Qu.rear&&Qu.level[i]==k)
	 	{
	 		n++;
	 		i++;
		 }
		 k=Qu.level[i];
		 if(n>max)
		    max=n;
	  } 
	return max;
 } 

3.總的代碼實現

#include<stdio.h>
#include<stdlib.h>
#define maxsize 100
typedef struct BTNode
{
	struct BTNode *lchild;
	struct BTNode *rchild;
	int data;
}BTNode;

typedef struct 
{
	BTNode *data[maxsize];   //保存隊列中的結點指針 
	int level[maxsize];     //保存data中相同下標結點的層次 
	int front,rear;
 }Que;
//二叉排序樹的插入
int Insert_BST(BTNode *&T,int key)
{
	if(T==NULL)
	{
		T=(BTNode *)malloc(sizeof(BTNode));
		T->lchild=T->rchild=NULL;
		T->data=key;
		return 1;
	}
	else 
	{ 
		if(key==T->data)
		   return 0;
		else if(key<T->data)
		  return Insert_BST(T->lchild,key);
		else 
		   return Insert_BST(T->rchild,key);
	} 
 } 
 
 void Visit (BTNode *p)
{
	if(p!=NULL)
	   printf("%d ",p->data); 
}
  //創建二叉排序樹 
 int Create_BST(BTNode *&T,int arry[],int n)
 {
 	int i=0;
 	T=NULL; 
 	while(i<n)
 	{
 		Insert_BST(T,arry[i]);
 		i++; 
	}
}

//遞歸算法求二叉樹的高度 
int getDepth(BTNode *T)
{
	int LD,RD;
	if(T==NULL)
	   return 0;
	else
	{
		LD=getDepth(T->lchild);
		RD=getDepth(T->rchild);
		return (LD>RD?LD:RD)+1; 
	}
}

//非遞歸求二叉樹的高度
/*採用層次遍歷的算法,設置變量level記錄當前結點所在的層數,設置變量last指向當前層的最右結點,
每次層次遍歷出隊時和last指針比較,若兩者相等,則層數加1,並讓last指向下一層的最右結點,直到遍歷完成*/
int Btdepth(BTNode *T)
{
	if(T==NULL)
	   return 0;
	int front,rear;   //初始化層次遍歷需要的循環隊列 
	front=rear=-1;
	BTNode *Que[maxsize];
	int last=0,level=0;
	BTNode *p; 
	
	Que[++rear]=T;
	while(front<rear)      //隊列不空 
	{
		p=Que[++front];
		if(p->lchild!=NULL)
			Que[++rear]=p->lchild;
		if(p->rchild!=NULL)
			Que[++rear]=p->rchild;
		if(front==last)
		{
		   level++;
		   last=rear;
		}
	}
	return level;
}
 
//求非空二叉樹的寬度
int BtWidth(BTNode *T)
{
	BTNode *p;
	int k,max,i,n;
	Que Qu;
	Qu.front=Qu.rear=-1;  //隊列爲空
	Qu.rear++;
	Qu.data[Qu.rear]=T;   //根節點指針入隊 
	Qu.level[Qu.rear]=1;   //根節點的層次爲1
	while(Qu.front<Qu.rear)
	{
		Qu.front++;  //出隊
		p=Qu.data[Qu.front];  //出隊結點
		k=Qu.level[Qu.front];   //出隊結點層次
		if(p->lchild!=NULL)     //左孩子進隊 
		{
			Qu.rear++;
			Qu.data[Qu.rear]=p->lchild;
			Qu.level[Qu.rear]=k+1;
		 } 
		 if(p->rchild!=NULL)    //右孩子入隊 
		 {
		 	Qu.rear++;
		 	Qu.data[Qu.rear]=p->rchild;
		 	Qu.level[Qu.rear]=k+1;
		 }
	 }//while
	 max=0;i=0;     //max保存同一層最多的結點個數
	 k=1;
	 while(i<Qu.rear)
	 {
	 	n=0;
	 	while(i<Qu.rear&&Qu.level[i]==k)
	 	{
	 		n++;
	 		i++;
		 }
		 k=Qu.level[i];
		 if(n>max)
		    max=n;
	  } 
	return max;
 } 
 
int main()
{
	BTNode *T;
	int arry[]={40,72,38,35,67,51,90,8,55,21};
	Create_BST(T,arry,10);
	int depth=getDepth(T);
	printf("遞歸二叉樹的高度:%d\n",depth); 
	int level=Btdepth(T);
	printf("非遞歸二叉樹的高度:%d\n",level); 
	int width=BtWidth(T);
	printf("二叉樹的最大的寬度:%d\n",width);

	
 } 

運行結果

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章