/**二叉樹的鏈式儲存實現隊列實現層序插入和層序遍曆棧實現非遞迴的二叉樹的遍曆 **/#include<stdio.h>#include<malloc.h>#include<math.h>#include<string.h>//二叉樹元素類型typedef char TElemType;//二叉樹節點 typedef struct BiTreeNode{TElemType QItem;struct BiTreeNode *lchild;struct BiTreeNode *rchild; } BiTreeNode,*BiTree;//棧節點 typedef struct StackNode{BiTree BNode;struct StackNode *next;//下一個}StackNode,*Stack;//隊列節點 typedef struct QueueNode{BiTree BNode;//儲存二叉樹的節點指標 struct QueueNode *rear;//隊尾,只有隊首的rear才是正真的隊尾 struct QueueNode *next;//元素的next是其相鄰靠近隊尾的元素 }QueueNode,*Queue;/**函式宣告 **/int InitStack(Stack &S);//初始化棧int Push(Stack &S,BiTree BNode);//入棧BiTree Pop(Stack &S);//出棧int IsEmptyStack(Stack S);//棧是否為空白int InitQueue(Queue &Q);//初始化隊列int InQueue(Queue &Q,BiTree BNode);//入隊BiTree DeQueue(Queue &Q);//出隊int IsEmptyQueue(Queue Q);//隊列是否為空白int InitBiTree(BiTree &T);//初始化二叉樹int CreateBiTree(BiTree &T,char *str);//層序建立二叉樹(非隊列實現)void Qcreate(BiTree &T,char *str);//層序建立二叉樹(隊列實現)void TravelLevel(BiTree T);//層序遍曆二叉樹(隊列實現)int IsEmptyBiTree(BiTree &T);//二叉樹是否為空白int PrintTree1(BiTree T);//遞迴二叉樹先序遍曆int PrintTree2(BiTree T);//遞迴二叉樹中序遍曆int PrintTree3(BiTree T);//遞迴二叉樹後序遍曆void PTravel(BiTree T);//非遞迴二叉樹先序遍曆void MTravel(BiTree T);//非遞迴二叉樹中序遍曆void LTravel(BiTree T);//非遞迴二叉樹後序遍曆/////////////////////////////////棧//////////////////////////////////////////////棧的初始化int InitStack(Stack &S){S=(Stack)malloc(sizeof(StackNode));if(!S){printf("初始化棧失敗!");return 0;}else{S->BNode=NULL;S->next=NULL;}}//入棧int Push(Stack &S,BiTree BNode){Stack p=S;Stack temp;//第一個元素if(S->BNode==NULL){S->BNode=BNode;S->next=NULL;return 1;} else{//構造插入節點 InitStack(temp);//入棧 temp->BNode=BNode;temp->next=S;S=temp;return 2;}} //出棧,並刪除棧頂元素BiTree Pop(Stack &S){BiTree newb;Stack temp=S;//只有一個元素if(S->next==NULL){InitBiTree(newb);newb=S->BNode;S->BNode=NULL;return newb;} else{S=S->next;return temp->BNode;}} //判斷棧是否為空白int IsEmptyStack(Stack S){if(S->BNode==NULL) return 1;else return 0;} //////////////////////////////隊列///////////////////////////////////////////////隊列初始化int InitQueue(Queue &Q){Q=(Queue)malloc(sizeof(QueueNode));if(!Q){return 0;}else{Q->BNode=NULL;Q->rear=NULL;Q->next=NULL;return 1;}} //入隊int InQueue(Queue &Q,BiTree BNode){//第一個元素 if(Q->BNode==NULL){Q->BNode=BNode;Q->rear=Q;Q->next=NULL;return 1;}else{//構造入隊元素 Queue newq;newq=(Queue)malloc(sizeof(QueueNode));newq->BNode=BNode;newq->next=NULL;newq->rear=NULL;Q->rear->next=newq;//插入 Q->rear=newq; //改變隊首的rear return 2;}} //出隊,返回隊首指標,並刪除之 BiTree DeQueue(Queue &Q){Queue m=Q;if(Q->next==NULL){//儲存僅有的一個元素InitQueue(m);m->BNode=Q->BNode;m->next=NULL;m->rear=NULL;//隊列置空Q->BNode=NULL;Q->rear=NULL;Q->next=NULL; }else{Q=Q->next;Q->rear=m->rear;}return m->BNode;} //判斷隊列是否為空白 int IsEmptyQueue(Queue Q){if(Q->BNode==NULL)return 1;else return 0;}//初始化二叉樹 int InitBiTree(BiTree &T){T=(BiTree)malloc(sizeof(BiTreeNode));if(!T){return 0;}else{T->QItem=NULL;T->lchild=NULL;T->rchild=NULL;return 1;}} /////////////////////////二叉樹//////////////////////////////////////////////// //二叉樹的構建,str為順序節點儲存的字元 int CreateBiTree(BiTree &T,char *str){BiTree m,q;q=T;int length,i,j;length=strlen(str);if(length<1&&length>31) return 0;q->QItem=str[0];for(i=2;i<=length;i++){m=(BiTree)malloc(sizeof(BiTreeNode));m->QItem= str[i-1];m->lchild=NULL; m->rchild=NULL;for(j=1;j<(int)(log10(i)/log10(2));j++)//log2(i)為要添加節點的上一層 {if((i/(int)pow(2,(int)(log10(i)/log10(2))-j))%2==0)//0為左孩子 {if(q->lchild==NULL){printf("輸入錯誤,第%d個節點無父節點\n",i);free(m);return 0;} q=q->lchild;}else{if(q->rchild==NULL){printf("輸入錯誤,第%d個節點無父節點\n",i);free(m);return 0;}q=q->rchild;}}//判斷左右孩子 if(i%2==0){q->lchild=m;printf("左插入%d\n",i); }else{q->rchild=m;printf("右插入%d\n",i); }q=T;}return 1; } //先序列印二叉樹(遞迴實現)int PrintTree1(BiTree T){BiTree q=T;if(q!=NULL){printf("%c ",q->QItem);PrintTree1(q->lchild);PrintTree1(q->rchild); }return 1;} //中序遍曆二叉樹(遞迴實現)int PrintTree2(BiTree T){BiTree q=T;if(q!=NULL){PrintTree2(q->lchild);printf("%c ",q->QItem);PrintTree2(q->rchild);}return 1;}//後序遍曆二叉樹(遞迴實現)int PrintTree3(BiTree T){BiTree q=T;if(q!=NULL){PrintTree3(q->lchild);PrintTree3(q->rchild);printf("%c ",q->QItem);}return 1;}//判斷二叉樹是否為空白int IsEmptyBiTree(BiTree &T){if(T==NULL){return 1;}else{return 0;}}//二叉樹的層序遍曆,隊列實現 void TravelLevel(BiTree T){Queue Q;InitQueue(Q);BiTree tree=T,m;InQueue(Q,tree);//根節點入隊while(IsEmptyQueue(Q)!=1){m=DeQueue(Q);printf("%c ",m->QItem);InQueue(Q,m->lchild);InQueue(Q,m->rchild);}}//二叉樹先序遍曆,非遞迴實現 (棧)void PTravel(BiTree T){Stack stack;BiTree t=T;InitStack(stack);while(IsEmptyStack(stack)!=1||IsEmptyBiTree(t)!=1){while(IsEmptyBiTree(t)!=1)//二叉樹非空 {printf("%c ",t->QItem);Push(stack,t);t=t->lchild;}if(IsEmptyStack(stack)!=1)//棧非空 {t=Pop(stack);t=t->rchild;}}} //二叉樹中序遍曆,非遞迴實現 (棧)void MTravel(BiTree T){Stack stack;BiTree t=T;InitStack(stack);while(IsEmptyStack(stack)!=1||IsEmptyBiTree(t)!=1){while(IsEmptyBiTree(t)!=1)//二叉樹非空 {Push(stack,t);t=t->lchild;}if(IsEmptyStack(stack)!=1)//棧非空 {t=Pop(stack);printf("%c ",t->QItem);t=t->rchild;}}}//二叉樹後序遍曆,非遞迴實現(棧)void LTravel(BiTree T){Stack stack;BiTree cur;//當前節點BiTree pre=NULL;//前一次訪問節點InitStack(stack);Push(stack,T);while(IsEmptyStack(stack)!=1){cur=stack->BNode;//當前節點無左右孩子則輸出//上次訪問節點不空且(上次訪問節點和當前節點的左孩子或右孩子相同),則輸出if((cur->lchild==NULL&&cur->rchild==NULL)||(pre!=NULL&&(pre==cur->lchild||pre==cur->rchild))){printf("%c ",cur->QItem);Pop(stack);pre=cur;}else{if(cur->rchild!=NULL)Push(stack,cur->rchild);if(cur->lchild!=NULL)Push(stack,cur->lchild);}}} //層序建立二叉樹(隊列實現)void Qcreate(BiTree &T,char *str){int len=strlen(str);int i=1;Queue Q;BiTree temp,b;InitQueue(Q);//根節點InitBiTree(b);b->QItem=str[0];InQueue(Q,b);T=b;while(IsEmptyQueue(Q)!=1){temp=DeQueue(Q);if(str[i]!='\0'){InitBiTree(b);b->QItem=str[i];InQueue(Q,b);temp->lchild=b;}i++;if(str[i]!='\0'){InitBiTree(b);b->QItem=str[i];InQueue(Q,b);temp->rchild=b;}i++;}}int main(){char s[80]="12345678";BiTree T=NULL;InitBiTree(T);//CreateBiTree(T,s);Qcreate(T,s);IsEmptyBiTree(T);printf("遞迴先序遍曆二叉樹:\n");PrintTree1(T);printf("\n非遞迴先序遍曆二叉樹:\n");PTravel(T); printf("\n遞迴中序遍曆二叉樹:\n");PrintTree2(T);printf("\n非遞迴中序遍曆二叉樹:\n");MTravel(T);printf("\n遞迴後序遍曆二叉樹:\n");PrintTree3(T);printf("\n非遞迴後序遍曆二叉樹:\n");LTravel(T);printf("\n層序遍曆二叉樹:\n");TravelLevel(T);printf("\n");return 1;}