数据结构中关于图以及相关算法的总结

1. 首先我们需要清楚的是有关图的相关概念,定义和相关术语,比如顶点的度、入度、初度、弧、有向完全图和无向完全图、路径和路径长度、简单路径、回路连通、连通图和连通分量、强连通图和强连通分量、权和网

① 简单路径:序列中顶点不重复的路径称为简单路径

② 连通图:如果图中任意两个顶点之间都连通那么称该图为连通图

③ 无向图中的极大连通子图称为连通分量

④ 强连通图:在有向图中如果对于每一对顶点都存在路径那么称该图为强连通图,其中的极大强连通子图称为强联通分量

2. 图的存储方式

主要有以下三种方式:① 邻接矩阵 ② 邻接表 ③ 边集

比较常用的两种是邻接矩阵和邻接表,邻接矩阵使用二维数组来表示图中顶点与顶点之间的关系,邻接表是为图中每一个顶点都创建一个单链表当前顶点与其他的邻居顶点都连接起来,我们在具体实现的时候并不是一定要创建单链表当前顶点与其余顶点连接起来可以根据选择的编程语言进行相应的改变,例如Java语言可以使用一个List集合来表示当前顶点与其余顶点的关系,集合中的每一个元素都是具有联系的

3. 图的遍历主要有两种方法:① 深度优先遍历 ② 广度优先遍历

这里需要注意区别于树的遍历的不同点,因为图是有可能产生回路的,所以我们在遍历图的时候需要增加一个标记用来标记当前的顶点或者是边是否之前被访问过了,假如访问过了那么我们直接跳过访问下一个顶点或者是边

4. 最小生成树算法

主要有两种算法: ① Prim算法 ② Kruskal算法

Prim算法核心:使用一个数组d来记录其余顶点到当前顶点的最短路径,每一次都是选择到当前顶点最短的边连接的顶点并且标记该顶点已访问,并且以当前顶点作为起点来检查是否需要更新当前顶点到其余顶点的最短路径,这个与Dijkstra算法有些地方是很类似的,可以对照着来进行理解

Kruskal算法核心:对图中的所有边从小到大进行排序,按照边权从小到大测试所有的边,如果当前测试的边不在同一个联通块中那么则将当前这条边加入到最小生成树中(使用并查集来检查当前的边是否在同一个集合中),否则加入这条边会生成一个回路,应该将其舍弃掉,重复执行上面的测试边的步骤直到所有的边数等于顶点数减1即可,假如结束的时候最小生成树的边数小于顶点数减1那么该图是不连通的

Kruskal算法思想比较简单,理解起来比Prim算法要好一点

这两种算法都是针对于无向图的

5. 最短路径算法

主要有以下四种:① Dijkstra算法 ② Bellman-Ford算法 ③ SPFA算法 ④ Floyd算法

考试中比较常考的有两种:Dijkstra算法和Floyd算法

Dijkstra算法与Prim算法是类似的,使用一个数组d来记录源点到其余顶点的最短路径(这个是Prim算法中的d数组记录是不一样的)一开始的时候先选择一个源点,然后每一次都是选择源点到其余顶点距离最短的顶点作为中间节点并且标记已访问,检查是否由于这个中间节点使得源点到其余顶点的路径最短,假如是那么更新源点到达其余顶点的路径

Floyd算法求解的是全源最短路径,即是求解图中任意顶点间的最短路径,算法思想比较简单,使用三层循环,检查以k作为中间顶点的时候,顶点i和j之间的路径是否变短,假如变短了那么更新i和j之间的路径,注意k需要将其放到最外层的循环

你可能感兴趣的:(图)