1. 程式人生 > >C語言二叉樹的實現

C語言二叉樹的實現

        二叉樹的儲存結構包含順序儲存結構和鏈式儲存結構,由於順序儲存結構很容易造成不必要的浪費,本人用的是鏈式儲存結構(注意在實際操作中最後 要釋放節點空間)。基本操作包括:遍歷二叉樹、先序遍歷的順序建立二叉樹、複製二叉樹、計算二叉樹深度、計算二叉樹結點個數。下面講一下實現程式碼:

        首先是定義結構型別:

typedef struct BiTNode{
	ElemType data;
	BiTNode *lchild;
	BiTNode *rchild;
}BiTNode,*BiTree;

        遍歷二叉樹:

void InOrderTraverse(BiTree T)
{
	if (T)
	{
		InOrderTraverse(T->lchild);
		printf("%c ", T->data);
		InOrderTraverse(T->rchild);
	}
}

        判斷T是否為空,如果T不為空樹,則遞迴讀取左子樹,輸出當前根節點的資料,遞迴讀取右子樹。

序遍歷的順序建立二叉樹:

BiTNode *CreateBiTree(BiTree T)
{
	ElemType ch;
	scanf("%c", &ch);
	if (ch == '#')
		T = NULL;
	else
	{
		T = (BiTNode *)malloc(sizeof(BiTNode));
		T->data = ch;
		T->lchild = CreateBiTree(T->lchild);
		T->rchild = CreateBiTree(T->rchild);
	}
	return T;
}

        該函式將#作為空的標誌,當輸入的字元為#的時候,T為空樹。如果不為空,先為T動態分配BiTNode型別的空間,將輸入字元的值賦值給樹T的資料域,遞迴呼叫CreateBiTree()來輸入T的左右子樹的資料。注意必須返回T的地址。

複製二叉樹:

BiTNode *Copy(BiTree T, BiTree NewT)
{
	if (T == NULL)
		NewT = NULL;
	else
	{
		NewT = (BiTNode *)malloc(sizeof(BiTNode));
		NewT->data = T->data;
		NewT->lchild = Copy(T->lchild, NewT->lchild);
		NewT->rchild = Copy(T->rchild, NewT->rchild);
	}
	return NewT;
}

        複製和建立個人覺得邏輯上是差不多的,只是將舊樹T的data賦值給新樹NewT的data,然後遞迴實現對左右子樹的複製。

        求二叉樹樹的深度:

int Depth(BiTree T)
{
	int m, n;
	if (T == NULL)
		return 0;
	else
	{
		m = Depth(T->lchild);
		n = Depth(T->rchild);
		if (m > n)
			return (m + 1);
		else
			return (n + 1);
	}
}

        先判斷數是否為空,如果為空,深度為0,則返回0。如果不為空,讓m等於左子樹的深度,n等於右子樹的深度,如果大於n則返回m+1(子樹的深度加上當前根等於樹的深度),否則返回n+1。

        求節點數:

int NodeCount(BiTree T)
{
	if (T == NULL)
		return 0;
	else
		return NodeCount(T->lchild) + NodeCount(T->rchild) + 1;
}

        判斷T是否為空樹,如果是的話,返回0,此時節點數為0個。如果不是,返回T的左子樹節點數、右子樹節點數、當前節點的和,得到所有節點的數量。

        加入main():

int main(void)
{
         BiTree T, NewT;
         int n, dep, num;
         T = NULL;
         NewT = NULL;
         printf("1.遍歷二叉樹\n2.建立二叉樹\n3.複製二叉樹\n4.計算二叉樹的深度\n5.計算節點的個數\n6.退出\n");
         while (1)
         {
                   printf("請選擇:");
                   scanf("%d",&n);
                   switch (n)
                   {
                   case 1:
                            InOrderTraverse(T);
                            printf("\n");
                            break;
                   case 2:
                            fflush(stdin);
                            T = CreateBiTree(T);
                            break;
                   case 3:
                            NewT = Copy(T,NewT);
                            InOrderTraverse(NewT);
                            printf("\n");
                            break;
                   case 4:
                            dep = Depth(T);
                            printf("深度為:%d\n",dep);
                            break;
                   case 5:
                            num = NodeCount(T);
                            printf("節點數為:%d\n",num);
                            break;
                   case 6:
                            exit(0);
                   }
         }
         return 0;
}