栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > C/C++/C#

树的存储结构

C/C++/C# 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

树的存储结构

双亲表示法
//结点结构
class PTNode{
    String data;//结点数据
    int parent;//双亲位置
}
class PTree{
    PTNode[] nodes = new PTnode[size];
    int r;//根的位置
    int n;//结点个数
}

双亲表示法如图所示:

以上存储结构,根据结点parent指针找到双亲结点的时间复杂度为O(1),parent为-1,表示
找到了树结点的根。结点的孩子需要遍历整个结构。

可以增加结点最左边孩子的域,可以叫长子域,这样可以得到结点的孩子。

可以增加结点右兄弟域来体现兄弟关系。

孩子表示法

每个结点有多个指针域,其中每个指针指向一棵子树的根结点。这种方法叫作多重链表表示法。

树的每个结点的度,它的孩子的个数是不同的。所以有两种解决方案:

  • 方案一

指针域的个数等于树的度(树的度是各个结点度的最大值)

缺点:树中各个结点度相差很大时,很浪费空间。如果树中结点度相差较少,就意味着开辟的空间被充分利用了。存储结构的缺点就变成了
优点。

  • 方案二(按需分配)

专门取一个位置来存储结点指针域的个数(degree)。

该方法空间利用率提高了,但是各个链表是不相同的结构,加上要维护结点的度的数值,运算上会带来损耗。

能否有更好的方法?减少空指针的浪费又能使结点结构相同?

我们为了遍历整棵树,把每个结点放到一个顺序存储结构的数组中,每个结点的孩子有多少是不确定的,所以再对每个结点
的孩子建立一个单链表体现它们的关系。

这就是 合理 的孩子表示法。


每个结点的孩子排列起来,以单链表作存储结构。n个结点有n个孩子链表,如果是叶子结点则此单链表为空。n个头指针又组成
一个线性表,采用顺序存储结构,存放进一个一位数组中。

//孩子结点
class CTNode{
    int child;//数组下标
    CTNode next;//孩子链表指针域
}
//表头结构
class CTBox{
    String data;//数据域
    CTNode firstchild;//第一个孩子指针
}
class Tree{
    CTBox[] ctBox = new CTBox[size];
    int r,n;
}
  • 优点:查找某个结点的某个孩子,或者找某个结点的兄弟,只需要查找这个结点的孩子单链表即可。遍历整棵树,对头结点数组遍历即可。
  • 缺点:如果想知道某个结点的双亲需要遍历整棵树。

可以针对此数据结构的缺点改进为 双亲孩子表示法

孩子兄弟表示法

双亲、孩子、兄弟角度研究树的存储结构。


规律:任意一棵树,它的结点的第一个孩子如果存在就是唯一的,它的右兄弟如果存在也是唯一的。因此我们可以设置两个指针,分别指向该结点的
第一个孩子和此结点的右兄弟。

clss CSNode{
    String data;
    CSNode firstchild;
    CSNode rightsib;
}


上面的结构查找某个结点的孩子很方便,如何查找双亲?可以增加一个parent指针域来解决查找双亲。

上图变形之后就是一棵二叉树,可以使用二叉树的特性

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/883962.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号