#include<iostream>
using namespace std;
typedef char TElemType;
typedef struct BiThrNode
{
TElemType data;
struct BiThrNode *lchild,*rchile;
int LTag,RTag;
}BiThrNode,*BiThrTree;
BiThrTree pre;
void CreateBiTree(BiThrTree& T )
{//按先序次序输入二叉树中结点的值(一个字符),创建二叉链表表示为二叉树T
char ch;
cin>>ch;
if(ch=='#')
T=NULL;//递归结束,建空树
else
{
T=new BiThrNode;//生成根结点
T->data=ch;//根结点数据域置为ch
CreateBiTree(T->lchild);//递归创建左子树
CreateBiTree(T->rchile);//递归创建右子树
}
}
void InThreading(BiThrTree p)
{//pre是全局变量,初始化时其右孩子指针为空,便于在树的最左点开始建线索
if(p)
{
InThreading(p->lchild);//左子树递归线索化
if(!p->lchild)//p的左孩子为空
{
p->LTag=1;//给p加上左线索
p->lchild=pre;//p的左孩子为指针指向pre(前驱)
}
else
p->LTag=0;
if(!pre->rchile)//pre的右孩子为空
{
pre->RTag=1;//给pre加上右线索
pre->rchile=p;//pre右孩子指针指向p(后继)
}
else
p->RTag=0;
pre=p;//保持pre指向p的前驱
InThreading(p->rchile);//右孩子递归线索化
}
}
void InOrderThreading(BiThrTree& Thrt,BiThrTree T)
{//中序遍历二叉树T,并将其中序线索化,Thrt指向头结点
Thrt=new BiThrNode;//建头结点
Thrt->LTag=0;//头结点有左孩子,若树非空,则其左孩子为树根
Thrt->RTag=1;//头结点的右孩子指针为右线索
Thrt->rchile=Thrt;//初始化时右指针指向自己
if(!T)
Thrt->lchild=Thrt;//若树为空,则左指针也指向自己
else
{
Thrt->lchild=T;pre=Thrt;//头结点的左孩子指向根,pre初值指向头结点
InThreading(T);//调用InThreading函数,对以T为根的二叉树进行中序线索化
pre->rchile=Thrt;//调用InThreading函数结束后,pre为最右结点,pre的右线索指向头结点
pre->RTag=1;
Thrt->rchile=pre;//头结点的右线索指向pre
}
}
//用非递归遍历中序遍历,即用迭代
void InOrderTraveerse(BiThrTree T)
{//T指向头结点,头结点的左链lchild指向根结点
//中序遍历二叉线索树T的非递归算法,对每个数据元素直接输出
BiThrTree p;
p=T->lchild;
while(p!=T)//当头指针不等于根结点 (即非空树)或者遍历结束
{
while(p->LTag==0)//当头指针有左子树 时
{
p=p->lchild;//一直迭代到最左下的叶子 (即沿左孩子向下)
}
cout<<p->data;//访问其左子树为空的结点,打印出来
while(p->RTag==1&&p->rchile!=T)//当头指针没有右子树时,且它的右子树不指向头结点 ,说明有后继
{
p=p->rchile;//沿右线索访问后继结点
cout<<p->data;//打印出来
}
p=p->rchile;//转向p的右子树,直到指回头结点,结束
}
}
int main()
{
BiThrTree Thrt,T;
CreateBiTree(T);
InOrderThreading(Thrt,T);
cout<<"中序遍历为:"<<endl;
InOrderTraveerse(Thrt);
}
二叉树的线索化
最新推荐文章于 2022-02-20 18:40:13 发布