今天,突然看到二叉树的来了兴致,就把二叉树的相关操作总结了一下!! 还望大家批评指正。
废话不多说 来代码:
#include"stdafx.h"
#include"Stack.h"
void CreateTree(BTree & T)
{
char ch;
cin>>ch;
if(ch=='*') T=nullptr;
else
{
T=new Tree();
T->k=ch;
CreateTree(T->left);
CreateTree(T->right);
}
}
//也可以用遍历的方法记录最大深度
int Tree_Depth(BTree T)//树的深度假如只有左子树 则深度为左子树深度+1,只有右子树深度为右子树深度+1,都有则为左右子树深度最大者+1.
{
if(T==nullptr)
{
return 0;
}
int leftd=Tree_Depth(T->left);
int rightd=Tree_Depth(T->right);
return (leftd > rightd) ? (leftd+1):(rightd+1);
}
//判断树是否为平衡二叉树(二叉树中任意结点的左右子树的深度相差不超过1,那么它就是一棵平衡二叉树。)
//采用后序遍历的方法判断每个节点的左右子树是否满足深度相差不超过1(并记录),最后遍历根节点从而判断是否为平衡二叉树
bool Is_Balance(BTree T,int &deep)
{
if(T==nullptr)
{
deep=0;
return true;
}
int left=0;
int right=0;
if(Is_Balance(T->left,left)&&Is_Balance(T->right,right))
{
int deepCha=left-right;
if(deepCha<=1 && deepCha >= -1)
{
deep=1 + (left>right? left:right);
return true;
}
}
return false;
}
bool Is_Balance_Tree(BTree T)
{
int deep=0;
return Is_Balance(T,deep);
}
//前序遍历
void inOrderTree(BTree T)
{
if(T==nullptr)
{
return ;
}
BTStack S;
create_Stack(S);
BTree p=T;
while(p!=nullptr||!IsEmpty(S))
{
if(p)
{
cout<<p->k<<" ";
Push(S,p);
p=p->left;
}
else
{
Pop(S,p);
p=p->right;
}
}
}
//中序遍历(利用栈)
void MidOrderTree_Stack(BTree T)
{
if(T==nullptr)
{
return ;
}
BTStack S;
create_Stack(S);
BTree p = T;
while(p!=nullptr||!IsEmpty(S))
{
if(p)
{
Push(S,p);
p=p->left;
}
else
{
Pop(S,p);
cout<<p->k<<" ";
p=p->right;
}
}
}
//中序遍历(不利用栈,利用子树的右孩子指针)
void MidOrderTree_NoStack(BTree T)
{
BTree p=T;
BTree tr;
while(p)
{
if(p->left==nullptr)
{
cout<<p->k<<" ";
p=p->right;
}
else
{
tr=p->left;
while(tr->right&&tr->right!=p)
{
tr=tr->right;
}
if(tr->right==nullptr)
{
tr->right=p;
p=p->left;
}
else
{
cout<<p->k<<" ";
tr->right=nullptr;
p=p->right;
}
}
}
}
//后序遍历
void FollowUpTree(BTree T)
{
if(T==nullptr)
{
return ;
}
BTStack S;
create_Stack(S);
BTree p = T;
BTree pr=p;//设置pr指向弹出栈的元素,用于判断p的右子树已弹出该弹出 p
Push(S,p);
p=p->left;
while(!IsEmpty(S))//后续遍历最后弹出根节点所以只判断栈是否为空
{
if(p&&p!=T)
{
Push(S,p);
p=p->left;
}
else
{
GetTop(S,p);//取栈顶元素
if(p->right&&p->right!=pr)//判断栈顶元素其孩子是否已弹出,如弹,出则弹出该元素
{
p=p->right;
}
else if(p->right==nullptr)
{
Pop(S,p);
pr=p;
cout<<p->k<<" ";
p=p->right;
}
else
{
Pop(S,p);//弹出有右孩子的父节点
cout<<p->k<<" ";
if(p==T&&p->k==T->k)//最后弹出根节点退出循环
{
break;
}
pr=p;
GetTop(S,p);//取栈顶防止再让其右孩子进栈
if(p->right!=pr)
{
p=p->right;
}
}
}
}
}
以上是Tree.cpp文件内容 也是完成操作的主要调用函数。
下面是主函数:
#include "stdafx.h"
#include<iostream>
using namespace std;
#include"Tree.h"
int _tmain(int argc, _TCHAR* argv[])
{
BTree T;
cout<<"请输入树中每个节点的值"<<endl;
cout<<"注:二三次输入分别为第一次输入左右孩子如果左或右孩子为空则输入“*”代替"<<endl;
CreateTree(T);
cout<<"您输入的树的深度为";
cout<<Tree_Depth(T)<<endl;
if(Is_Balance_Tree(T))
{
cout<<"您输入的二叉树为平衡二叉树"<<endl;
}
else
{
cout<<"您输入的二叉树不为平衡二叉树"<<endl;
}
cout<<"该二叉树的前序遍历为:"<<endl;
inOrderTree(T);
cout<<endl<<"该二叉树的中序遍历(利用栈)为:"<<endl;
MidOrderTree_Stack(T);
cout<<endl<<"该二叉树的中序遍历(不利用栈)为:"<<endl;
MidOrderTree_NoStack(T);
cout<<endl<<"该二叉树的后序遍为:"<<endl;
FollowUpTree(T);
return 0;
}
例如:如上图输入这个二叉树:1 2 4 * * 5 7 * * * 3 * 6 * *
输出为:
其他文件 是一些函数声明,树,栈结构声明和一些栈的操作。
可到这下载:点击打开链接 提取码 8bc5