#include<stdio.h>
#include<stdlib.h>
#include<string.h>
typedef enum {link,Thread} PointerTag;
typedef char TElemType;
typedef struct Node
{
TElemType data;
PointerTag Ltag,Rtag; //增加的线索标记
struct Node *lchild;
struct Node *rchild;
} BiTree,*BiThrTree;
BiThrTree pre; //全局变量,始终指向刚刚访问过的结点
void InThreading(BiThrTree p)
{
if(p)
{
InThreading(p->lchild);//递归左子树线索化
if(p->lchild==NULL) //没有左孩子
{
p->Ltag=Thread; //前驱线索
p->lchild=pre; //左孩子指针指向前驱
}
if(pre->rchild==NULL) //前驱没有右孩子
{
pre->Rtag=Thread; //后继线索
pre->rchild=p; //前驱右孩子指针指向后继
}
pre=p; //保持pre指向p的前驱
InThreading(p->rchild); //递归线索化右子树
}
}
BiThrTree InOrderThrTree(BiThrTree &T) //中序线索化二叉树
{
BiThrTree head; //head为头结点的指针
head=(BiThrTree )malloc(sizeof(BiThrTree));
head->lchild=T; //头结点的左孩子指向根结点,1操作
head->rchild=head; //右孩子指向自身
pre=head; //3操作
InThreading(T); //线索化,更改Rtag和Ltag
pre->Rtag=Thread;
pre->rchild=head; //4操作
head->rchild=pre; //2操作
return head;
}
//遍历线索二叉树
void InOrderTraverse_Thr(BiThrTree T)
{
BiThrTree p;
p=T->lchild; //p指向头结点
while(p!=T) //当p不等于头结点,循环继续,空树或结束时,p==T
{
while(p->Ltag==link) //当有左孩子时
p=p->lchild;
printf("%c",p->data);
while(p->Rtag==Thread&&p->rchild!=T)//没有右孩子且不等于头结点
{
p=p->rchild; //p指向后继
printf("%c",p->data);
}
p=p->rchild; //p进入右子树根
}
}
//按前序建立二叉树
void creatBiTree(BiThrTree &T)
{
char ch;
scanf("%c",&ch);
if (ch == '#')
{
T = NULL;
return;
}
else
{
T = (BiThrTree)malloc(sizeof(BiTree));
T->data = ch;
T->Ltag=link;// 初始化都为link
T->Rtag=link;
creatBiTree(T->lchild);
creatBiTree(T->rchild);
}
}
int main()
{
BiThrTree T,head;
creatBiTree(T);
head=InOrderThrTree(T);
InOrderTraverse_Thr(head);
return 0;
}
运行结果