树的定义和基本运算解读
合集下载
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
2. 孩子表示法
孩子表示法主要描述的是结点的孩子关系。由于
每个结点的孩子个数不定,所以利用链式存储结构更 加适宜。举例:
root
0 1 2 3 4 5 6 7 8 9
A C B E D F G H I J
2
^
1 5 ^
4 ^
3
^ 6 ^
^
7 ^ ^ ^
图 5-4
8
9 ^
在C语言中,这种存储形式定义如下: #define MAX_TREE_NODE_SIZE 10 typedef struct ChildNode{ int child; //该孩子结点在一维数组中的下标值 //指向下一个孩子结点 struct ChileNode *next;
可以将双亲表示法和孩子表示法结合起来,即将一维
数组元素增加一个表示双亲结点的域parent,用来指 示结点的双亲在一维数组中的位置。
获取给定结点第i个孩子的操作算法实现:
int Child(ChildTree T, int node, int i) { if (node<0||node>=T.n) return -2; p=T.item[node].firstchild; j=1; while (p&&j!=i) { p=p->next; j++;} if (!p) return -2; else return p->child; }
森林 是m(m≥0)棵互不相交的树的集合。 在树结构中,结点之间的关系又可以用家族关系 描述,定义如下: 孩子、双亲 结点子树的根称为这个结点的孩子, 而这个结点又被称为孩子的双亲。
子孙 以某结点为根的子树中的所有结点都被称 为是该结点的子孙。
祖先 从根结点到该结点路径上的所有结点。
兄弟 同一个双亲的孩子之间互为兄弟。
3. 孩子兄弟表示法
孩子兄弟表示法也是一种链式存储结构。它通过 描述每个结点的一个孩子和兄弟信息来反映结点之间 的层次关系,其结点结构为:
firstchild
item
nextsibli ng
其中,firstchild为指向该结点第一个孩子的指针, nextsibling为指向该结点的下一个兄弟,item是数据元素 内容。举例:
5.1 树
5.1.1 1. 定义 树是一种常用的非线性结构。我们可以这样定义: 树是n(n≥0)个结点的有限集合。若n=0,则称为空 树;否则,有且仅有一个特定的结点被称为根,当n>1 时,其余结点被分成m(m>0)个互不相交的子集T1, T2,...,Tm,每个子集又是一棵树。由此可以看出, 树的定义和基本运算
树的定义是递归。
A
B
E F
A
C
G H
D
I J
K
L
M
(a)
(b)
(c)
图 5-1
结点 数据元素的内容及其指向其子树根的分支统 称为结点。
结点的度 结点的分支数。
终端结点(叶子) 度为0的结点。
非终端结点 度不为0的结点。 结点的层次 树中根结点的层次为1,根结点子树 的根为第2层,以此类推。 树的度 树中所有结点度的最大值。 树的深度 树中所有结点层次的最大值。 有序树、无序树 如果树中每棵子树从左向右的排 列拥有一定的顺序,不得互换,则称为有序树,否则 称为无序树。
下标 AA B E 0 1 2 3 4 5 6 7 8 9
info A B C D E F G H I J
B
F F
C C
DD GG
HH I
E
I
JJ
paren t -1 0 0 0 1 1 3 6 6 6图 5-3Fra bibliotek类型定义:
#define MAX_TREE_NODE_SIZE 100 typedef struct { TEntryType info; int parent;
T
A ^ B ^ E ^ F ^ ^ C D ^ G ^
^ H
图 5-5
^ I
^ J ^
在C语言中,这种存储形式定义如下: typedef struct CSNode{ EntryType item; struct CSNode *firstchild,*nextsibling; }CSNode,*CSTree; void AllChild(CSTree T, CSTree p) //输出树中p指针所指结点的所有孩子信息 { q=p->fisrtchild; while (q) { printf(“%c”,q->item); q=q->nextsibling; } }
(6)遍历树Traverse(T) 对树遍历的主要目的是将非线性结构通过遍历过程 线性化,即获得一个线性序列。树的遍历顺序有两种, 一种是先序遍历,即先访问根结点,然后再依次用同 样的方法访问每棵子树;另一种是后序遍历,即先依
5.1.2
树的存储结构
1. 双亲表示法
树的双亲表示法主要描述的是结点的双亲关系。
}CNode;
typedef struct{ TEntryType info; CNode *firstchild; }TNode; //结点信息 //指向第一个孩子结点的指针
typedef struct { TNode item[MAX_TREE_NODE_SIZE]; int n,root; //n为树中当前结点的数目,root为根结点在一维 数组中的位置 }ChildTree; 这种存储结构的特点是寻找某个结点的孩子比较 容易,但寻找双亲比较麻烦,所以,在必要的时候,
} ParentNode;
typedef struct { ParentNode item[MAX_TREE_NODE_SIZE]; int n; //树中当前的结点数目
}ParentTree;
这种存储方法的特点是寻找结点的双亲很容易, 但寻找结点的孩子比较困难。 算法实现举例: int Parent(ParentTree T,int node) { if (node<0||node>=T.n) return -2; else return T.item[node].parent; }
堂兄弟 双亲在同一层的结点互为堂兄弟。
2. 树的基本运算
常用操作: (1) 构造一个树 CreateTree (T)
(2)清空以T为根的树 ClearTree(T)
(3)判断树是否为空 TreeEmpty(T) (4)获取给定结点的第i个孩子 Child(T,node,i)
(5)获取给定结点的双亲 Parent(T,node)