学习线索二叉树

  • 何谓二叉树
  • 线索二叉树的诞生——中序序列
  • 线索的价值
  • 线索的建立
  • 线索的问题
  • 线索化二叉树节点结构
  • 线索二叉树建立
  • 总结

何谓二叉树

二叉树(binary tree)是指树中节点的度不大于2的有序树。

作为树的一种,相较于其他的树,二叉树在存储结构和算法上较为简单,并且一般树可以轻松转化为二叉树,因而备受重视。

线索二叉树的诞生——中序序列

在了解线索和线索二叉树前,我们或许应该了解线索二叉树是为了解决什么诞生。

首先,在这里,我们先建立一个简单的二叉树作为讨论的参考对象,用ABCDEF建立一个完全二叉树。


现在,我们需要寻找该二叉树的 中序序列 中某个节点的前驱。假设,我们要找的是A点的前驱吧。我们可以迅速的找到E。这个一眼就能看出。

如果现在我们把这个二叉树扩展到深度N=非常大的数,比如10000。现在,让你找出A的前驱和后驱,那么我们需要花费多少时间呢?

答案是很快,因为这棵树现在还是完全二叉树呢,哈哈。不过如果不是完全二叉树呢?

是的,或许就像部分朋友想到的那样,我们需要对整个树去进行一次遍历,假设这个树的深度是10000,那我们就需要访问10000个节点才能保证一定能找到A的前驱是谁。

事实上,我们实际问题中的二叉树,可能层数会比这更深,如果当一项任务需要大量访问节点的前驱后时,它对内存的开销,必然是巨大的。

而线索化,就是为了解决该问题诞生。

线索的价值

我们现在知道了,在寻找节点前驱后继时,我们将面临巨大的麻烦。而这的源头跟二叉树本身的非线性结构有关。

那么我们应该如何处理它呢?

如果你的机子硬盘只用了10%,但是你的运行内存已经被你的任务跑满的时候,你会怎么做呢?我们可以让硬盘的一部分,作为虚拟内存为你工作,为悲惨的运行内存分担一份压力,对吧?

没错,如果我们在寻找前驱后继这件事上,运行时间花费代价过大,我们可以适当牺牲地一小部分存储空间,来帮我们处理这个问题。

前驱后继,说到底,是一种线性结构,而我们正好有接触过这样一种线性结构,它的数据存储结构并非连续的。

对,链表,如果我们以链表的方式,为每个节点添加他的前驱后继节点的地址,我们只需花小小的代价获得巨大的效率提升。

线索的建立

线索的建立方式如下:

如果某结点的左子树为空,则该结点的左孩子指针指向其前驱结点。
如果某结点的右子树为空,则该结点的右孩子指针指向其后继结点。

如此建立的指针便是我们所说的线索。

由于节点的建立方式是将本来的空指针转为填入一个前驱或后继的指针。因此在这一步,实际的空间代价几乎为0。

线索的问题

这时候只要仔细一想,我们便会发现线索的引入带来了另一个问题:我怎么知道这个指针,指的是线索还是子树呢?

于是,我们采用了最简单的办法:标志位。

我们这样定义该标志位的规则:

当标志位tag=0,它表示该指针指向子树
当标志位tag=1,他表示该指针指向前驱或后继

在添加完标志位后,我们的节点结构便确定下来了:

相较于最初的节点,添加两个标志位。

总体的空间代价便是2个标志位 * 节点数。

线索化二叉树节点结构

简单的线索二叉树构成

// 节点数据 TelemType
typedef struct TelemType;
// 节点结构
typedef struct TreNode{TelemType data;TreNode *lchild, *rchild;Tag lTag ,rTag;
}

线索二叉树建立

void inThreading(ThrBiTree T, ThrBiTree &pre){  if(T){  inThreading(T->lchild, pre);//左子树线索化  if(!T->lchild){//当前结点的左孩子为空  T->lTag = Thread;  T->lchild = pre;  }else{  T->lTag = Link;  }  if(!pre->rchild){//前驱结点的右孩子为空  pre->rTag = Thread;  pre->rchild = T;  }else{  pre->rTag = Link;  }  pre = T;          inThreading(T->rchild, pre);//右子树线索化  }

总结

线索二叉树,是一种用空间置换时间的一种算法。它通过让二叉树在本来的非线性结构上增加了一层线性结构,来提高二叉树在前驱后继查询的效率。它的建立最好是在最开始建立树的时候便建立。

这是我第一次在CSDN上发布文章,如果有任何意见,见解或是其中有任何错误,欢迎各位大佬指点一二。

深入了解,学习线索二叉树相关推荐

  1. 线索二叉树,画图教你秒懂线索二叉树(线索二叉树的建立和简单操作)逻辑代码分析

    数据结构专升本学习,线索二叉树 前言 前面我们学习树和二叉树的一些基本操作,今天我们学习一个新的知识,学习一下线索二叉树,线索二叉树是由二叉链存储结构变化而来的(我们先得有个二叉链树,再做处理),就是 ...

  2. 深入学习二叉树(二) 线索二叉树

    深入学习二叉树(二) 线索二叉树 1 前言 在上一篇简单二叉树的学习中,初步介绍了二叉树的一些基础知识,本篇文章将重点介绍二叉树的一种变形--线索二叉树. 2 线索二叉树 2.1 产生背景 现有一棵结 ...

  3. 数据结构与算法(八)-二叉树(斜二叉树、满二叉树、完全二叉树、线索二叉树)...

    前言:前面了解了树的概念和基本的存储结构类型及树的分类,而在树中应用最广泛的种类是二叉树 一.简介 在树型结构中,如果每个父节点只有两个子节点,那么这样的树被称为二叉树(Binary tree).其中 ...

  4. 8.遍历二叉树、线索二叉树、森林

    思考 一.什么遍历二叉树.线索二叉树.森林?(What) 0.二叉树遍历一共(4种) 1.二叉树先序遍历 2.二叉树中序遍历 3.二叉树后序遍历 4.遍历分析 5.遍历二叉树 6.二叉树层次遍历 7. ...

  5. 线索二叉树详解(C语言版)

    文章目录 一.定义 二.结构 三.常用操作 结语 附录 一.定义 前面学习了二叉树,在操作过程中发现了几个问题: 问题一:二叉树如何才能实现从一个指定结点开始遍历呢?         问题二:在二叉树 ...

  6. c语言线索二叉树作用,C语言递归实现线索二叉树

    本文实例为大家分享了C语言递归实现线索二叉树的具体代码,供大家参考,具体内容如下 描述:将二叉树中结点的空左孩子指针域指向前驱结点,将空的右孩子指针域指向后继结点. code: #pragma war ...

  7. 中序线索二叉树(C语言实现)

    目录 1.线索二叉树的定义: 2.线索二叉树的存储结构: 3.创建中序线索二叉树 4.遍历中序线索二叉树 5.在中序线索二叉树上查找任意结点的中序前驱结点 6.在中序线索二叉树上查找任意结点的中序后继 ...

  8. C语言数据结构之线索二叉树

    C语言数据结构之线索二叉树 tips:前些天学习了二叉树的相关操作,今天来总结一下线索二叉树的操作. 线索二叉树:对二叉树以某种次序遍历得到序列中的前驱和后继,其中指向结点前驱和后继的指针称为线索,再 ...

  9. 数据结构与算法(6-4)线索二叉树

    优势:便于在中序遍历下,查找前驱和后继. 前驱/后继含义:AB中,A是B前驱,B是A后继. ltag=0时:lchild指向左孩子                ltag=1时:lchild指向前驱 ...

最新文章

  1. PYTHON编程导论群问题汇总(三)
  2. c#_Task用法总结
  3. Spring中IoC的入门实例
  4. 走的走的居然飞起来了……
  5. apache.camel_Apache Camel 2.23发布
  6. 前端学习(173):格式化文本二
  7. 机器学习 | 网络搜索及可视化
  8. 字节跳动1/3员工不支持取消大小周!库克称iPhone将采用可回收材料生产;清华博士接亲被要求现场写代码|极客头条...
  9. Bailian2820 Ancient Cryptogram【密码】
  10. pom文件各标签解释
  11. DM860步进电机接线及拨码
  12. Massive MIMO中正交导频pilot序列的MATLAB生成方法
  13. c# DevExpress Gridview 设置表格背景颜色
  14. 硬盘无法访问设备未就绪,里面的数据怎么找回
  15. pytorch-gradual-warmup-lr安装
  16. 计算机上的游戏怎么不见了怎么办,电脑自带小游戏消失怎么找回?高手教你找回电脑自带小游戏...
  17. html div flex,CSS中flex布局详解
  18. 软件设计的哲学:第十六章 修改现有代码
  19. 递归:这帮小兔子崽子、汉诺塔游戏+习题复习
  20. 2021-1-29 美赛前MATLAB的学习笔记(基础、脚本、代数方程、微分方程、矩阵初步、作图基础)

热门文章

  1. python与脚本语言
  2. Hoxx使用保姆级教程【附截图| 安卓苹果电脑】
  3. CH340进行STM32单片机程序烧录
  4. SpringBoot之整合Redis分析和实现-基于Spring Boot2.0.2版本
  5. select属性标签
  6. window10开启移动热点
  7. 计算机打开查看方式默认是什么样,如何设置电脑文件夹默认查看方式
  8. python界面编程
  9. linux系统打开远程端口,linux下3种检测远程端口是否打开的方法
  10. 用stm32F103核心板的GPIOA端一管脚接一个LED,GPIOB端口一引脚接一个开关(用杜邦线模拟代替)。采用中断模式编程,当开关接高电平时,LED亮灯;接低电平时,LED灭灯。