在最近学习中需要用到图的相关知识,但很多知识已经忘记,遂重新再过一遍图。
图按照有无方向分为无向图和有向图。无向图由顶点和边构成,有向图由顶点和弧构成。弧有 弧尾和弧头之分。
图按照边或弧的多少分稀疏图和稠密图。如果任意两个顶点之间都存在边叫完全图,有向的叫有向完全图。若无重复的边或顶点到自身的边则叫简单图。
图中顶点之间有邻接点、依附的概念。无向图顶点的边数叫做度,有向图顶点分为入度和出度。
图上的边或弧上带权则称为网。
图中顶点间存在路径,两顶点存在路径则说明是连通的,如果路径最终回到起始点则称为环,当中不重复叫简单路径。若任意两顶点都是连通的,则图就是连通图,有向则称强连通图。图中有子图,若子图极大连通则就是连通分量,有向的则称强连通分量。
无向图中连通且n个顶点n-1条边叫生成树。有向图中一顶点入度为 0其余顶点入度为1的叫有向树。一个有向图由若干棵有向树构成生成森林。
图的存储结构
邻接矩阵:图的邻接矩阵(Adjacency Matrix)存储方式是用两个数组来表示图。一个一维
数组存储图中顶点信息,一个二维数组(称为邻接矩阵)存储图中的边或弧的信息
无向图的邻接矩阵
由上图我们可以看出无向图的边数组是一个对称矩阵。
同样,我们求顶点Vi的所有邻接点就是将矩阵中第i行元素扫描一遍,边数组 arc[i][j]为 1就是邻接点。
有向图的邻接矩阵
由于有向图是单向的,所以有向图的邻接矩阵可能并不对称。而判断有向图某个顶点的邻接点的方法与无向图一样,查找矩阵中对应的点是否为1。
虽然邻接矩阵是一种不错的图存储结构,但其实对于变数相对顶点较少的图,这种结构是存在对存储空间极大的浪费的。以下图为例:
该邻接矩阵中除了arc[1][0]外,其他的存储空间全都浪费了。因此我们考虑另外一种存储结构方式来表示:邻接表
邻接表:
1.图中顶点用一个一维数组存储,当然,顶点也可以用单链表来存储,不过数组可以较容易 地读取顶点信息,更加方便。另外,对于顶点数组中,每个数据元素还需要存储指向第一 一个邻接点的指针,以便于查找该顶点的边信息。
2.图中每个顶点Vi的所有邻接点构成一个线性表,由于邻接点的个数不定,所以用单链表存 储,无向图称为顶点Vi的边表,有向图则称为顶点Vi 作为弧尾的出边表。
无向图的邻接表结构
从图中我们知道,顶点表的各个结点由data 和firstedge两个域表示,data 是数据域,存储顶点的信息,firstedge 是指针域,指向边表的第一一个结点, 即此顶点的第一个邻接点。边表结点由adjvex 和next两个域组成。adjvex 是邻接点域,存储某顶点的邻接点在顶点表中的下标,next 则存储指向边表中下一个结点的指针。比如V1顶点与V0、V2互为邻接点,则在V1的边表中,adjvex 分别为V0的0和V2的2。
若要判断顶点Vi到Vj是否存在边,只需要测试顶点Vi的边表中adjvex是否存在结点Vj的下标j就行了。若求顶点的所有邻接点,其实就是对此顶点的边表进行遍历,得到的adjvex域对应的顶点就是邻接点。
有向图的邻接表
有向图的邻接表结构与无向图相似。