您的位置:首页 > 其它

(广度、深度)遍历二叉树

2013-12-16 15:03 253 查看
闲着无聊,偶然看到广度遍历二叉树(采用队列的结构),而深度遍历二叉树采用(栈的结构);

根据广度遍历二叉树的原理,自己仔细想了哈!没有参考资料(采用栈的存储方式)对二叉树进行深度遍历

#include
using namespace std;
typedef int ElemType;
//二叉树的节点
typedef struct BiTNode
{
ElemType value;
struct BiTNode *left,*right;
}BiTNode,*BiTree;
//一个队列节点
typedef struct QueNode
{
BiTNode bNode;
struct  QueNode *next;
}QueNode;
//队列的指针(头指针,尾指针)
typedef struct
{
QueNode *front;
QueNode *rear;
}QuePtr;
void initQue(QuePtr &q)
{
q.front=q.rear=NULL;
}
//判断队列数是否为空
bool isEmpty(QuePtr &q)
{
return q.front==NULL;
}
void pushQueue(QuePtr &q,BiTNode e)
{
//首先创建一个节点
QueNode *qNode=(QueNode*)malloc(sizeof(QueNode));
qNode->bNode=e;
//每次创建一个必须设置为NULL
qNode->next=NULL;
//如果为空
if (isEmpty(q))
{   //队列的头指针和尾指针指向新建的节点
q.front=q.rear=qNode;
}else{
q.rear->next=qNode;
//让队尾指针始终指向新建的节点
q.rear=qNode;
}
}
void popQueue(QuePtr &q)
{
if (!isEmpty(q))
{
QueNode *temp=q.front;
q.front=temp->next;
//将队列中第一个元素删除
free(temp);
}
}

//访问队列节点
void visitQueNode(QueNode *e)
{ //输出二叉树中的元素
cout<bNode.value<<",";
}
//手动创建二叉树
BiTNode *create_1(BiTNode *head)
{
char a;
a=getchar();
//scanf("%c",&a);
if (a=='#')
{
return NULL;
}else
{
if(!(head=(BiTNode *)malloc(sizeof(BiTNode))))
exit(0);
head->value=a;
head->left=create_1(head->left);
head->right=create_1(head->right);
}
return head;
}

//自动创建一颗二叉树
/*              1
2       3
4     5     6    7
8 9  10 11 12 13 14 15

**/
BiTNode *create_2(BiTNode *head)
{
if (head->value<8)
{
BiTNode *left=(BiTNode *)malloc(sizeof(BiTNode));
BiTNode *right=(BiTNode *)malloc(sizeof(BiTNode));
if (!left||!right)
{
exit(0);
}
head->left=left;
left->value=head->value*2;
head->right=right;
right->value=head->value*2+1;
create_2(left);
create_2(right);
}else
{
head->left=NULL;
head->right=NULL;
}
}
//广度优先遍历二叉树(通常是加入到一个队列中去的)
void breadthTraversal(BiTNode *head)
{
//首先初始化一个队列
QuePtr q;
initQue(q);
//将头节点入队
pushQueue(q,*head);
//循环的条件是队列不能为空,每次加入到队列中,后面最后进入队列下一个指针域为NULL
// while (!isEmpty(q))
//在这里q.front指针不断的往后移动
while(q.front)
{
//访问这个头节点
visitQueNode(q.front);
if (q.front->bNode.left!=NULL)
{ //如果左节点存在,那么加入到队列中去
pushQueue(q,*(q.front->bNode.left));
}
if (q.front->bNode.right!=NULL)
{//如果右节点存在,那么加入到队列中去
pushQueue(q,*(q.front->bNode.right));
}
//将位于队列中第一个元素出队
popQueue(q);
}
}
//深度优先遍历一个二叉树,通常是采用的栈的结构
//************************
///*********** 栈 *************
///************************
///************************
//栈的节点
typedef struct StackNode{
BiTNode bNode;
struct StackNode *next;
}StackNode;
//栈指针
typedef struct
{
StackNode *top,*bottom;
}StackPtr;
//初始化一个栈(顶,低)指针
void initStatck(StackPtr &stack)
{
stack.bottom=stack.top=NULL;
}
//将二叉树入栈
void pushStack(StackPtr &stack,BiTNode bNode)
{
StackNode *staNode=(StackNode*)malloc(sizeof(StackNode));
staNode->bNode=bNode;
staNode->next=NULL;
//如果栈为空,
if (stack.bottom==NULL)
{
stack.bottom=stack.top=staNode;
}else{
//这里是将新建的节点指向栈顶
staNode->next=stack.top;
//栈顶指向新建的节点
stack.top=staNode;
}
}
//访问栈中的节点
void visitStaNode(StackNode *e)
{ //输出二叉树中的元素
cout<bNode.value<<",";
}
//当左右孩子都判断完了,那么出栈
void popStack(StackPtr &stack)
{   //首先判断栈顶不为空
if (stack.top)
{
StackNode *temp=stack.top;
stack.top=temp->next;
//说明满足出栈的要求,开始输出节点
visitStaNode(temp);
free(temp);
}
}
//深度优先遍历二叉树
void depthTraversal(StackPtr &stack,BiTNode *head)
{
if(head)
{  //此节点存在入栈
pushStack(stack,*head);
//开始判断左孩子是否存在
depthTraversal(stack,head->left);
//右孩子是否存在
depthTraversal(stack,head->right);
//运行到这一步,分为两种情况:
//1、左右孩子不存在
//2、左右孩子,已经遍历了,并出栈了
popStack(stack);
}
}
//求一个数的深度(depth),节点数(nCount),叶子数(leaf)
int depth,nCount,leaf;
int TreeLength(BiTNode *head)
{
//首先判断这个节点是否存在,不存在还回0
if(head)
{
int lDepth=TreeLength(head->left);
int rDepth=TreeLength(head->right);
//当对一个左孩子,右孩子访问完之后,及可判断这个节点
nCount++;
//在两个左右深度之间判断那个大
int max=lDepth>rDepth?lDepth:rDepth;
//判断叶子:即左右深度为0
if (lDepth==0&&rDepth==0)
{
leaf++;
}
return max+1;
}else{
return 0;
}

}
int main(int arg,const char *argv[])
{
BiTNode *head=(BiTNode *)malloc(sizeof(BiTNode));
//12#4##35###
//head=create_1(head);
head->value=1;
create_2(head);
StackPtr stack;
initStatck(stack);
cout<<"深度优先遍历二叉树:"<
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: