1.概念

按照某种遍历方式对二叉树进行遍历,可以把二叉树中所有结点排序为一个线性序列。在改序列中,除第一个结点外每个结点有且仅有一个直接前驱结点;除最后一个结点外每一个结点有且仅有一个直接后继结点。这些指向直接前驱结点和指向直接后续结点的指针被称为线索(Thread),加了线索的二叉树称为线索二叉树。

当用二叉链表作为二叉树的存储结构时,因为每个结点中只有指向其左、右儿子结点的指针,所以从任一结点出发只能直接找到该结点的左、右儿子。在一般情况下靠它无法直接找到该结点在某种遍历序下的前驱和后继结点。如果在每个结点中增加指向其前驱和后继结点的指针,将降低存储空间的效率。

我们可以证明:在n个结点的二叉链表中含有n+1个空指针。因为含n个结点的二叉链表中含有个指针,除了根结点,每个结点都有一个从父结点指向该结点的指针,因此一共使用了n-1个指针,所以在n个结点的二叉链表中含有n+1个空指针。

因此可以利用这些空指针,存放指向结点在某种遍历次序下的前驱和后继结点的指针。这种附加的指针称为线索,加上了线索的二叉链表称为线索链表,相应的二叉树称为线索二叉树(ThreadedBinaryTree)。根据线索性质的不同,线索二叉树可分为前序线索二叉树、中序线索二叉树和后序线索二叉树三种。

建立线索二叉树,或者说对二叉树线索化,实质上就是遍历一颗二叉树。在遍历过程中,访问结点的场所是检查当前的左,右指针域是否为空,将它们改为指向前驱结点或后续结点的线索。为实现这一过程,设指针pre始终指向刚刚访问的结点,即若指针p指向当前结点,则pre指向它的前驱,以便设线索。

2.代码

//BinaryThreadTree  线索二叉树
// 1.用户前序输入二叉树数据
// 2.对二叉树进行线索化 lchild ltag Data rtag rchild
//   ltag/rtag 左右标记位  0:有孩子结点 link  1: 存储前驱或后继结点线索 Thread
// 3.中序迭代遍历输出二叉树数据#include <stdio.h>
#include <stdlib.h>typedef char ElemType;//线索存储标志位
//link(0): 指向左右孩子 | 表示当前结点的左指针(*lchild)或右指针(*rchild) 指向对应的左或右孩子
//Thread(1): 指向前驱后继线索 | 表示当前结点的左指针(*lchild)或右指针(*rchild) 指向对应的前驱或后继元素
typedef enum
{Link,                                   //link=0,Thread                                  //Thread=1
}PointerTag;//BinaryThreadTree Node 线索二叉树结点结构
typedef struct BiThrNode
{ElemType data;struct BiThrNode *lchild, *rchild;PointerTag ltag;PointerTag rtag;
}BiThrNode, *BiThrTree;                     //*BiThrTree: 指向结点的指针为树//全局变量 始终指向刚刚访问过的结点
BiThrTree pre; //前一个结点/头结点指针//创建一颗二叉树,约定用户遵照前序遍历方式输入数据
void CreateBiThrTree(BiThrTree *T)         //BiThrTree *T: T为指向树的指针 | 二级指针
{ElemType c;scanf("%c", &c);if (' ' == c){*T = NULL;}else{*T = (BiThrNode*)malloc(sizeof(BiThrNode));(*T)->data = c;(*T)->ltag = Link;                    //标志位赋初值,默认所有结点有左右孩子    (*T)->rtag = Link;CreateBiThrTree(&(*T)->lchild);       //递归法为左右子节点赋值CreateBiThrTree(&(*T)->rchild);}
}//中序遍历线索化 | 改变无左或右孩子结点的tag标志位,使其指向前驱或后继(形成首尾相连的双向链表)
void InThreading(BiThrTree T)
{if (T)                                    //若不为空树{InThreading(T->lchild);               //递归左孩子线索化if (!T->lchild)                       //若该结点没有左孩子,设置Tag为Thread{T->ltag = Thread;T->lchild = pre;}if (!pre->rchild)                     //*****//{pre->rtag = Thread;pre->rchild = T;}pre = T;InThreading(T->rchild);               //递归右孩子线索化}
}//初始化二叉树T 开始时的头指针pre + 中序遍历线索化 + 收尾:头尾相连
//参数 *p: 指向树的头指针
//参数  T : 要操作的二叉树
void InOrderThreading(BiThrTree *p, BiThrTree T)
{//*p = (BiThrTree)malloc(sizeof(BiThrTree));*p = (BiThrNode *)malloc(sizeof(BiThrTree));   //头指针分配内存(*p)->ltag = Link;                         //结点指针操作结点:赋值(*p)->rtag = Thread;(*p)->rchild = *p;                         //头指针右侧初始化指向自己if (!T){(*p)->lchild = *p;                     //空二叉树,指向自己}else{ (*p)->lchild = T;                      //头指针左侧 指向要操作的对象pre = *p;                              //初始化头指针preInThreading(T);                        //中序遍历线索化 后pre 变成最后一个结点Tpre->rchild = *p;                      //最后一个结点 指向 头指针pre->rtag = Thread;(*p)->rchild = pre;                    //头指针 指向 最后一个结点}
}//打印输出
void myvisit(char c)
{printf("%c", c);
}
//中序遍历二叉树,迭代输出
//参数 T : 头指针
void InOrderTraverse(BiThrTree T)
{BiThrTree p;p = T->lchild;                             //从头指针位置迭代输出while (p != T)                             //若为结点非空{while (p->ltag == Link)                //输出最下层左结点数据{p = p->lchild;}myvisit(p->data);while (p->rtag == Thread && p->rchild != T)  //输出右结点下一个结点{p = p->rchild;myvisit(p->data);}p = p->rchild;                         //迭代}
}
int main()
{BiThrTree P, T = NULL;CreateBiThrTree(&T);                       //约定用户前序输入二叉树数据InOrderThreading(&P, T);                   //线索化二叉树printf("中序遍历输出结果为:");InOrderTraverse(P);                        //中序遍历二叉树,迭代输出printf("\n");return 0;
}

3.结果

线索二叉树(Binary Thread Tree)相关推荐

  1. (原)数据结构——线索二叉树

    原文地址:http://www.cnblogs.com/Security-Darren/p/4716082.html 转载务必注明出处! 线索二叉树的思想来源于二叉树的存储结构中,存在一些空的指针域, ...

  2. 线索二叉树原理及前序、中序线索化(Java版)

    转载 原文地址:https://blog.csdn.net/UncleMing5371/article/details/54176252 一.线索二叉树原理 前面介绍二叉树原理及特殊二叉树文章中提到, ...

  3. 线索二叉树(基于链表存储树结点)

    有以下场景 如果使用中序遍历,那么得到的顺序是:HDIBEAFCG,可以得知A的前驱结点为E,后继结点为F.但是,这种关系的获得是建立在完成遍历后得到的.如果我们每次想得到某个节点的前驱或者后继,都要 ...

  4. 编程基础 - 线索二叉树 (Threaded Binary Tree)

    编程基础 - 线索二叉树 (Threaded Binary Tree) 返回分类:全部文章 >> 基础知识 返回上级:编程基础 - 二叉树 (Binary Tree) 本文将介绍线索二叉树 ...

  5. C语言实现线索二叉树Threaded Binary Tree (附完整源码)

    C语言实现线索二叉树Threaded Binary Tree 树节点定义 实现以下7个接口 完整实现和main测试源码 树节点定义 typedef struct Node {int data; /** ...

  6. 『数据结构与算法』解读树(Tree)和二叉树(Binary Tree)!

    『数据结构与算法』解读树(Tree)和二叉树(Binary Tree)! 文章目录 一. 树 1.1. 树的定义 1.2. 树的基本术语 1.3. 树的性质 二. 二叉树 2.1. 二叉树的定义 2. ...

  7. [CareerCup] 4.7 Lowest Common Ancestor of a Binary Search Tree 二叉树的最小共同父节点

    4.7 Design an algorithm and write code to find the first common ancestor of two nodes in a binary tr ...

  8. 【数组递归构造二叉树】LeetCode 108. Convert Sorted Array to Binary Search Tree

    LeetCode 108. Convert Sorted Array to Binary Search Tree Solution1:我的答案 构造二叉树利用递归 /*** Definition fo ...

  9. 【数据结构】二叉树 (Binary Tree)

    目录 一. 什么是树? 二. 二叉树 特殊二叉树 二叉树的性质 二叉树的存储 二叉树的遍历 二叉树的基本操作 一.什么是树? 之前咱们学习了一些简单的数据结构,如顺序表,链表,这些都是线性结构,线性结 ...

  10. 二叉树 Binary Tree

    我怀着激动的心 走上了这颗树 今天是2021年11月12日 今天开始上树!!!!!! 生活中的树形结构: 树:  根节点: 一棵树有且只有一个根节点就是最上面的节点 兄弟节点: 每一行的节点  它们具 ...

最新文章

  1. 140万!香港大学设高额博士奖学金
  2. 博士毕业后,想继续科研,想进高校任教,需要什么条件呢?
  3. 什么是内卷?华为内部这篇文章读懂
  4. 植物的意识,是我们的错觉吗?
  5. Htc Vive VR 手势识别插件教程 1.1 版本(附1.0版本教程PDF)
  6. ffmpeg:Codec for stream 0 does not use global headers but container format requires global headers
  7. python中最大值最小值平均值_来自lis的Python平均值、最大值、最小值
  8. 大端模式小端模式 主机序网络序
  9. 几种开发时安全验证的实现
  10. centos7搭建hadoop
  11. 没有workstation_这才是Win10的旗舰版:WorkStation版独享功能测试
  12. Cookie学习总结
  13. mybatis --XML 映射配置文件
  14. Microsoft Access 2002中文版标准培训教程pdf
  15. Excel:带有相关单元格引用的Python xlwings复制粘贴公式
  16. IT 认证考试--软考--(中级项目)嵌入式系统设计师1:嵌入式系统设计师介绍
  17. 超好用的jQuery插件
  18. 计算机不定时黑屏,宏基acer 4736ZG不定时黑屏,时亮时不亮通病维修
  19. Promise的基本用法以及作用
  20. Redis学习(1)——下载与配置[转]

热门文章

  1. [2019杭电多校第四场][hdu6623]Minimal Power of Prime
  2. Javascript倒计时 支持自定义样式
  3. 泥瓦匠 5 年 Java 的成长感悟(下)
  4. 登陆模块防止恶意用户SQL注入攻击
  5. 介绍一个基于SpringBoot2的脚手架项目
  6. Python 目录及文件操作(os.模块)
  7. 正确使用 realloc()
  8. 微信公众号开发 ----微信服务的接入(1)
  9. 乐至天气预报软件测试,乐至天气预报15天
  10. pytorch如何增加维度_Pytorch中的LSTM:如何添加/更改序列长度维度?-问答-阿里云开发者社区-阿里云...