算法源码之非递归创建/遍历二叉树

来源:互联网 发布:迅雷 linux 编辑:程序博客网 时间:2024/05/18 17:01

     递归创建二叉树很简单,主要使用系统提供的栈,效率不是很高。将隐式栈转换为显示栈,就归结为非递归形式了。

     在前序、中序、后序非递归创建二叉树中,后序创建稍微绕了一点。

     同样,本文没有分析其原理、以及算法的时间、空间复杂度,这些东西在设计算法的时候要考虑,

     将其现于纸上,繁琐。

#include<stdio.h>#include<stdlib.h>#define SIZE 8typedef struct BTree{    char data;struct BTree *LChild;struct BTree *RChild;}BTree;typedef struct Stack{    BTree *bt;}Stack;void createBTree(){BTree *bt,*root,*p,*q;char ch;int top=-1;Stack s[SIZE];ch=getchar();root=bt=(BTree*)malloc(sizeof(BTree)); //先创建根结点bt->data=ch;top++;s[top].bt=bt;                      //根结点地址入栈do{while(bt!=NULL){            //若当前结点不为空则,创建左孩子 ch=getchar(); if(ch==' '){              //若输入空格,则代表结点为空 bt->LChild=NULL;     bt=bt->LChild; } else {   bt->LChild=(BTree*)malloc(sizeof(BTree));//若输入的不为空格    bt->LChild->data=ch;         //则分配空间,建立左结点top++;s[top].bt=bt->LChild;        //并将创建的结点地址入栈bt=bt->LChild;             //让bt指向当前刚创建的结点}};                         // 若上面的循环结束,此时左孩子创建完毕/if(top!=-1){              //出栈 bt=s[top].bt; top--;ch=getchar();if(ch==' '){ bt->RChild=NULL; bt=bt->RChild;}else { //若输入的字符不是空格,则对刚出栈的结点创建右子树   bt->RChild=(BTree*)malloc(sizeof(BTree));   bt->RChild->data=ch;   top++;   s[top].bt=bt->RChild; //并将刚创建的结点地址入栈   bt=bt->RChild;     //让bt指向当前刚创建的结点}}  //只要bt不为空,或者top不等于-1,就继续做循环}while(bt!=NULL||top!=-1);printf("二叉树创建完毕!\n");                         //中序非递归遍历        top=-1;  //创建完二叉树,栈已经为空了,故可以重复利用printf("中序非递归遍历结果\n");p=root;  //将根结点赋给pdo{      //只要p不为空,或者top不等于-1,就继续做循环while(p!=NULL){ top++;         s[top].bt=p;//结点入栈 p=p->LChild;//继续遍历,直到左孩子为空};if(top!=-1){ p=s[top].bt; //根出栈 top--; printf(" %c",p->data);//访问根结点 p=p->RChild;    //若有右孩子,则访问}}while(p!=NULL||top!=-1);printf("\n");printf("前序非递归遍历结果\n");top=-1;p=root;do{   while(p!=NULL){  printf(" %c",p->data);//访问根结点     top++; s[top].bt=p; p=p->LChild; //中序遍历左子树   };   if(top!=-1){    p=s[top].bt;top--;p=p->RChild;//中序遍历右子树   }}while(p!=NULL||top!=-1);printf("\n");  printf("后序非递归遍历结果\n"); //后序非递归遍历top=-1;q=NULL;p=root;while(p!=NULL||top!=-1){while(p!=NULL){ top++; s[top].bt=p; p=p->LChild;};if(top!=-1){ p=s[top].bt; if((p->RChild==NULL)||(p->RChild==q)){  printf(" %c",p->data);  q=p;  top--;  p=NULL; } else p=p->RChild;}};printf("\n");}void main(){printf("输入非空字符代表非叶结点,输入空格代表叶节点\n");  createBTree();}

运行示例: