本贴为《数据结构》课程服务.
1. 主要内容
- 二叉树的先序、中序、后序遍历.
- 不准用递归.
2. 代码
2.1 潘佳豪
- 自己写栈, 真-不偷懒.
- 后序遍历有复杂的条件, 还有 while 循环的嵌套, 功力深厚.
- 居然还用文本在程序里画一棵树, 必成大器啊!
#include <iostream>
#include <malloc.h>
using namespace std;
#define MAXSIZE 1000
typedef int ElemType;
typedef struct TNode
{
ElemType data;
TNode *left;
TNode *right;
} TNode,*Tree;
typedef struct Queue
{
TNode *data[MAXSIZE];
int front;
int rear;
} queue;
typedef struct Stack
{
TNode *data[MAXSIZE];
int top;
} stack;
void BuildTree(Tree &root,int &index);
void InitQueue(queue *q);
void EnQueue(queue *q, Tree data);
void DeQueue(queue *q, Tree &data);
bool QueueEmpty(queue *q);
void BFP(Tree root);
void InitStack(stack *s);
void Push(stack *s, Tree data);
void Pop(stack *s, Tree &data);
Tree Top(stack *s);
bool StackEmpty(stack *s);
void PreOrder(Tree root);
void InOrder(Tree root);
void PostOrder(Tree root);
int main()
{
Tree tree;
int index = -1;
BuildTree(tree,index);
cout<<"构建的树:"<<endl
<<"1 2 "<<endl
<<"2 4 0 "<<endl
<<"3 5 -1 7 8 "<<endl
<<"4 -1 3 6 -1 -1 -1 "<<endl
<<"5 -1 -1 -1 -1 "<<endl<<endl;
//层级遍历
cout<<"层级遍历的结果;";
BFP(tree);
//先序遍历
cout<<"先序遍历的结果:";
PreOrder(tree);
//中序遍历
cout<<"中序遍历的结果:";
InOrder(tree);
//后序遍历
cout<<"后序遍历的结果:";
PostOrder(tree);
return 0;
}
//
//构建树
// 2
// 4 0
// 5 -1 7 8
// -1 3 6 -1 -1 -1
// -1 -1 -1 -1
void BuildTree(Tree &root,int &index)
{
index++;
ElemType temp[] = {2,4,5,-1,3,-1,-1,-1,0,7,6,-1,-1,-1,8,-1,-1};
if(temp[index] == -1)
{
root = NULL;
return;
}
else
{
root = (TNode*)malloc(sizeof(TNode));
root->data = temp[index];
BuildTree(root->left,index);
BuildTree(root->right,index);
}
}
//
//队列
//
void InitQueue(queue *q)
{
q->rear = 0;
q->front = 0;
}
void EnQueue(queue *q, Tree data)
{
if((q->rear + 1) % MAXSIZE == q->front)
{
return;
}
q->data[q->rear++] = data;
q->rear %= MAXSIZE;
}
void DeQueue(queue *q, Tree &data)
{
if(q->rear == q->front)
{
return;
}
data = q->data[q->front++];
q->front %= MAXSIZE;
}
bool QueueEmpty(queue *q)
{
return q->front == q->rear;
}
void BFP(Tree root)
{
queue q;
InitQueue(&q);
EnQueue(&q,root);
while (!QueueEmpty(&q))
{
Tree temp;
DeQueue(&q,temp);
cout<<temp->data<<" ";
if(temp->left) EnQueue(&q,temp->left);
if(temp->right) EnQueue(&q,temp->right);
}
cout<<endl<<endl;
}
//
//栈
//
void InitStack(stack *s)
{
s->top = 0;
}
void Push(stack *s, Tree data)
{
if(s->top >= MAXSIZE)
{
return;
}
s->data[s->top++] = data;
}
void Pop(stack *s, Tree &data)
{
if(s->top == 0)
{
return;
}
data = s->data[--s->top];
}
Tree Top(stack *s)
{
return s->data[s->top-1];
}
bool StackEmpty(stack *s)
{
return s->top == 0;
}
void PreOrder(Tree root)
{
stack s;
InitStack(&s);
Tree temp = root;
while(!StackEmpty(&s) || temp)
{
if(temp)
{
cout<<temp->data<<" ";
Push(&s,temp);
temp = temp->left;
}
else
{
Pop(&s,temp);
temp = temp->right;
}
}
cout<<endl<<endl;
}
void InOrder(Tree root)
{
stack s;
InitStack(&s);
Tree temp = root;
while(!StackEmpty(&s) || temp)
{
if(temp)
{
Push(&s,temp);
temp = temp->left;
}
else
{
Pop(&s,temp);
cout<<temp->data<<" ";
temp = temp->right;
}
}
cout<<endl<<endl;
}
void PostOrder(Tree root)
{
stack s;
InitStack(&s);
Push(&s,root);
Tree temp;
Tree lastpop = NULL;
while(!StackEmpty(&s))
{
while(Top(&s)->left)
{
Push(&s,Top(&s)->left);
}
while(!StackEmpty(&s))
{
if(lastpop == Top(&s)->right || Top(&s)->right == NULL)
{
cout<<Top(&s)->data<<" ";
lastpop = Top(&s);
Pop(&s,temp);
}
else if(Top(&s)->right != NULL)
{
Push(&s, Top(&s)->right);
break;
}
}
}
cout<<endl<<endl;
}
2.2 莫峦奇
后序遍历是"左右中",把左右互换就是"右左中", 逆序即为"中左右" (先序). 用这种方式, 可以使用先序遍历的相同方式来实现它. 唯一的区别就是需要使用一个栈, 逆序输出. 问题的转换是多么地重要!
#include<iostream>
#include<stack>
using namespace std;
//二叉树数据结构
typedef struct TreeNode
{
char data;
struct TreeNode *Leftchild;
struct TreeNode *Rightchild;
TreeNode(char c)
{
data=c;
Leftchild=NULL;
Rightchild=NULL;
}
} TreeNode,*Tree;
//创建二叉树
void CreateTree(Tree &p)
{
char c;
cin>>c;
if(c=='#') p=NULL;
else
{
p=new TreeNode(c);
cout<<"请输入"<<p->data<<"的左子树: ";
CreateTree(p->Leftchild);
cout<<"请输入"<<p->data<<"的右子树: ";
CreateTree(p->Rightchild);
}
}
//先序遍历
void PreOrder(Tree &T)
{
stack<Tree> S;
Tree p=T;
while(p||!S.empty())
{
if(p)
{
cout<<p->data<<" ";
S.push(p);
p=p->Leftchild;
}
else
{
p=S.top()->Rightchild;
S.pop();
}
}
}
//中序遍历
void InOrder(Tree &T)
{
stack<Tree> S;
Tree p=T;
while(p||!S.empty())
{
if(p)
{
S.push(p);
p=p->Leftchild;
}
else
{
p=S.top();
cout<<p->data<<" ";
p=p->Rightchild;
S.pop();
}
}
}
//后序遍历
void PostOrder(Tree &T)
{
Tree p=T;
stack<Tree> S;
stack<char> SS;
while(p||!S.empty())
{
if(p)
{
SS.push(p->data);
S.push(p);
p=p->Rightchild;
}
else
{
p=S.top()->Leftchild;
S.pop();
}
}
while(!SS.empty())
{
cout<<SS.top()<<" ";
SS.pop();
}
}
int main()
{
Tree p=NULL;
cout<<"创建二叉树,请输入根节点(#表示节点为空): ";
CreateTree(p);
cout<<"先序遍历: ";
PreOrder(p);
cout<<endl;
cout<<"中序遍历: ";
InOrder(p);
cout<<endl;
cout<<"后序遍历: ";
PostOrder(p);
return 0;
}