二叉树的创建,递归遍历,非递归遍历

二叉树(BinaryTree)是n(n≥0)个结点的有限集,它或者是空集(n=0),或者由一个根结点及两棵互不相交的、分别称作这个根的左子树和右子树的二叉树组成。

二叉树不是树,仅仅是和树相同的结构

 

这是二叉树的创建,递归遍历,非递归遍历。没有注释,一些被注释掉的函数也可以用,个人感觉挺好。

 

 /*********************** 二叉树的创建,递归遍历,非递归遍历,可以说是二叉树一般算法了 使用dev c++编译通过 2010/08/08 ***********************/ #include<stdio.h> #include<stdlib.h> #define maxsize 100 int increment=10; typedef struct bitnode { char data; struct bitnode *lchild; struct bitnode *rchild; }*bitree; typedef struct queue_bitnode { bitree v; struct queue_bitnode *next; }; typedef struct queue_bitree { queue_bitnode *front; queue_bitnode *rear; }; typedef struct stack_bitnode { bitree v; }; typedef struct stack_bitree { stack_bitnode *base; stack_bitnode *top; int stacksize; }; void create_bitree(bitree &T) { char ch; printf("请输入元素值以完成二叉树/n"); scanf("%c",&ch); if(ch==' ') T=NULL; else { T=(bitnode *)malloc(sizeof(bitnode)); T->data=ch; create_bitree(T->lchild); create_bitree(T->rchild); } } void PreorderTraverse(bitree &T) { if(T) { printf("%c",T->data); PreorderTraverse(T->lchild); PreorderTraverse(T->rchild); } } void InorderTraverse(bitree &T) { if(T) { InorderTraverse(T->lchild); printf("%c",T->data); InorderTraverse(T->rchild); } } void PostorderTraverse(bitree &T) { if(T) { PostorderTraverse(T->lchild); PostorderTraverse(T->rchild); printf("%c",T->data); } } void init_queue_bitree(queue_bitree &q) { q.front=q.rear=(queue_bitnode *)malloc(sizeof(bitnode)); if(!q.front) exit(0); q.front->next=NULL; } void enqueue_bitree(queue_bitree &q,bitree T) { struct queue_bitnode *p; p=(queue_bitnode *)malloc(sizeof(bitnode)); if(!p) exit(0); p->v=T; p->next=NULL; q.rear->next=p; q.rear=p; } void dequeue_bitree(queue_bitree &q,bitree &T) { if(q.rear==q.front) { printf("空队列/n"); exit(0); } queue_bitnode *p; p=q.front->next; T=p->v; q.front->next=p->next; if(p==q.rear) q.rear=q.front; free(p); } int empty_queue_bitree(queue_bitree &q) { if(q.rear==q.front) return 1; else return 0; } void LayorderTraverse(bitree T) { queue_bitree q; init_queue_bitree(q); if(T) enqueue_bitree(q,T); while(!empty_queue_bitree(q)) { dequeue_bitree(q,T); printf("%c ",T->data); if(T->lchild) enqueue_bitree(q,T->lchild); if(T->rchild) enqueue_bitree(q,T->rchild); } } //二叉树树的叶子个数 int leaf_bitree(bitree &T) { if(!T) return 0; else if(!T->lchild&&!T->rchild) return 1; else return leaf_bitree(T->lchild)+leaf_bitree(T->rchild); } //二叉树树的深度 int depth_bitree(bitree &T) { int depthl,depthr; int depth=0; if(!T) depth=0; else { depthl=depth_bitree(T->lchild); depthr=depth_bitree(T->rchild); depth=(depthl>depthr?depthl:depthr)+1; } return depth; } /* typedef struct stack_bitnode { bitree v; } typedef struct stack_bitree { stack_bitnode *base; stack_bitnode *top; int stacksize; }; */ void init_stack_bitree(stack_bitree &s) { s.base=(stack_bitnode *)malloc(sizeof(stack_bitnode)*maxsize); if(!s.base) exit(0); s.top=s.base; s.stacksize=maxsize; } void push(stack_bitree &s,bitree T) { if(s.top-s.base>=s.stacksize) { s.base=(stack_bitnode *)realloc(s.base,sizeof(stack_bitnode)*(s.stacksize+increment)); if(!s.base) exit(0); s.top=s.base+s.stacksize; s.stacksize+=increment; } s.top->v=T; s.top++; //printf("/n入栈一次/n"); } void pop(stack_bitree &s,bitree &T) { if(s.base==s.top) { printf("空队列/n"); exit(0); } T=(--s.top)->v; //printf("/n出栈一次/n"); } int empty_stack_bitree(stack_bitree s) { if(s.base==s.top) return 1; else return 0; } int getTop_stack_bitree(stack_bitree s,bitree &T) { if(s.top==s.base) return 0; T=(--s.top)->v; return 1; } /* //非递归先序遍历 void PreorderTraverse_nonrecur(bitree T) //要义在于遍历的时候,访问一个节点,然后将其入栈,再遍历其左子树,完事后 //最后出栈的是根树,再遍历其右子树 { bitree p; p=T; stack_bitree s; init_stack_bitree(s); while(p||!empty_stack_bitree(s)) { if(p) { printf("%c",p->data); push(s,p); p=p->lchild; } else { pop(s,p); p=p->rchild; } } } */ void PreorderTraverse_nonrecur(bitree T) // 要义在于遍历时候访问节点,再将节点的右子树入栈,继续访问下去。 { bitree p; p=T; stack_bitree s; init_stack_bitree(s); while(p||!empty_stack_bitree(s)) { if(p) { printf("%c",p->data); push(s,p->rchild); p=p->lchild; } else { pop(s,p); } } } //非递归中序遍历 void InorderTraverse_nonrecur(bitree T) { bitree p; p=T; stack_bitree s; init_stack_bitree(s); while(p||!empty_stack_bitree(s)) { if(p) { push(s,p); p=p->lchild; } else { pop(s,p); printf("%c",p->data); p=p->rchild; } } } /* void InorderTraverse_nonrecur(bitree T) { stack_bitree s; init_stack_bitree(s); bitree p; p=T; push(s,p); //根先入栈 while(!empty_stack_bitree(s)) { while(getTop_stack_bitree(s,p)&&p) { push(s,p->lchild); //printf("压栈1/n"); //一直压到最下的左子树 } pop(s,p); //退空指针 //退左子树的做左孩子 //printf("退栈2/n"); if(!empty_stack_bitree(s)) { pop(s,p); //退左孩子,访问左孩子 //printf("退栈/n"); printf("%c",p->data); push(s,p->rchild); //压右孩子 //printf("压栈3/n"); } } }*/ int main() { bitree T; create_bitree(T); printf("先序遍历/n"); PreorderTraverse(T); printf("/n"); printf("中序遍历/n"); InorderTraverse(T); printf("/n"); printf("后序遍历/n"); PostorderTraverse(T); printf("/n"); printf("层次遍历/n"); LayorderTraverse(T); printf("/n"); //printf("%c /n",T->data); printf("树的叶子个数 %d/n",leaf_bitree(T)); printf("树的深度 %d/n",depth_bitree(T)); printf("先序遍历非递归/n"); //PreorderTraverse_nonrecur(T); printf("中序遍历非递归/n"); InorderTraverse_nonrecur(T); system("pause"); } //abcd e fg hi

 

哈哈,再添加下后续遍历的非递归算法,在之前看到的一些后序非递归的算法里发现还要重构树和节点的结构,所以就停了下来,知道找到了比较容易的代码。

void PostorderTraverse(bitree &T) { bitree p=T; stack_bitree s; init_stack_bitree(s); bitree pre; while((p!=NULL)||!empty_stack_bitree(s)) { if(p!=NULL) { push(s,p); p=p->lchild; } else { p=gettop_stack_bitree(s); if((p->rchild!=NULL)&&(pre!=p->rchild)) { p=p->rchild; } else { p=pre=gettop_stack_bitree(s); printf("%c",p->data); pop(s,p); p=NULL; } } } }

你可能感兴趣的:(二叉树的创建,递归遍历,非递归遍历)