1. 程式人生 > >二叉樹建立及前序中序後序輸出精講

二叉樹建立及前序中序後序輸出精講

疑問:為什麼我是無限制的輸入資料:解答:二叉樹需要有一定的規律,最起碼節點的個數需要是2的n次方減一才能構成一個樹 還有就是考慮空節點問題,葉節點的NEXT必須為空才能結束所以說必須將樹設計好 才能輸入. #include<malloc.h> // malloc()等
 #include<stdio.h> // 標準輸入輸出標頭檔案,包括EOF(=^Z或F6),NULL等
 #include<stdlib.h> // atoi(),exit()






#define ClearBiTree DestroyBiTree // 清空二叉樹和銷燬二叉樹的操作一樣


typedef struct BiTNode
 { 
    int data; // 結點的值
    BiTNode *lchild,*rchild; // 左右孩子指標
 }BiTNode,*BiTree;


char Nil=0; // 設整型以0為空
void visit(int e)
 { printf("%d ",e); // 以整型格式輸出
 }
 void InitBiTree(BiTree &T)
 { // 操作結果:構造空二叉樹T
   T=NULL;
 }


 void CreateBiTree(BiTree &T)
 { // 演算法6.4:按先序次序輸入二叉樹中結點的值(可為字元型或整型,在主程中定義),
   // 構造二叉連結串列表示的二叉樹T。變數Nil表示空(子)樹。修改
   char number;
   scanf("%d",&number); // 輸入結點的值
   if(number==Nil) // 結點的值為空
     T=NULL;
   else // 結點的值不為空
   { T=(BiTree)malloc(sizeof(BiTNode)); // 生成根結點
     if(!T)
       exit(0);
     T->data=number; // 將值賦給T所指結點
     CreateBiTree(T->lchild); // 遞迴構造左子樹
     CreateBiTree(T->rchild); // 遞迴構造右子樹
   }
 }


 void DestroyBiTree(BiTree &T)
 { // 初始條件:二叉樹T存在。操作結果:銷燬二叉樹T
   if(T) // 非空樹
   { DestroyBiTree(T->lchild); // 遞迴銷燬左子樹,如無左子樹,則不執行任何操作
     DestroyBiTree(T->rchild); // 遞迴銷燬右子樹,如無右子樹,則不執行任何操作
     free(T); // 釋放根結點
     T=NULL; // 空指標賦0
   }
 }


 void PreOrderTraverse(BiTree T,void(*Visit)(int))
 { // 初始條件:二叉樹T存在,Visit是對結點操作的應用函式。修改演算法6.1
   // 操作結果:先序遞迴遍歷T,對每個結點呼叫函式Visit一次且僅一次
   if(T) // T不空
   { Visit(T->data); // 先訪問根結點
     PreOrderTraverse(T->lchild,Visit); // 再先序遍歷左子樹
     PreOrderTraverse(T->rchild,Visit); // 最後先序遍歷右子樹
   }
 }


 void InOrderTraverse(BiTree T,void(*Visit)(int))
 { // 初始條件:二叉樹T存在,Visit是對結點操作的應用函式
   // 操作結果:中序遞迴遍歷T,對每個結點呼叫函式Visit一次且僅一次
   if(T)
   { InOrderTraverse(T->lchild,Visit); // 先中序遍歷左子樹
     Visit(T->data); // 再訪問根結點
     InOrderTraverse(T->rchild,Visit); // 最後中序遍歷右子樹
   }
 }


  void PostOrderTraverse(BiTree T,void(*Visit)(int))
 { // 初始條件:二叉樹T存在,Visit是對結點操作的應用函式
   // 操作結果:後序遞迴遍歷T,對每個結點呼叫函式Visit一次且僅一次
   if(T) // T不空
   { PostOrderTraverse(T->lchild,Visit); // 先後序遍歷左子樹
     PostOrderTraverse(T->rchild,Visit); // 再後序遍歷右子樹
     Visit(T->data); // 最後訪問根結點
   }
 }


 void main()
 {
   BiTree T;
   InitBiTree(T); // 初始化二叉樹T
   printf("按先序次序輸入二叉樹中結點的值,輸入0表示節點為空,輸入範例:1 2 0 0 3 0 0\n");
   CreateBiTree(T); // 建立二叉樹T
   printf("先序遞迴遍歷二叉樹:\n");
   PreOrderTraverse(T,visit); // 先序遞迴遍歷二叉樹T
   printf("\n中序遞迴遍歷二叉樹:\n");
   InOrderTraverse(T,visit); // 中序遞迴遍歷二叉樹T
   printf("\n後序遞迴遍歷二叉樹:\n");
   PostOrderTraverse(T,visit); // 後序遞迴遍歷二叉樹T
 }