持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第30天,点击查看活动详情
从给定图中任意指定的顶点出发,按照某个原则系统地访问图中的其他顶点,每个顶点仅仅被访问一次,得到由该图中顶点组成的一个序列,这个过程称为图的遍历。图的遍历通常采用两种方式,它们分别是深度优先搜索与广度优先搜索。在下面的讨论中,假设被遍历的图采用邻接表存储方法。需要提醒的是,由于图G=(V,E)中顶点集合V与边的集合E中元素的排列是任意的,在采用邻接表存储以后,如果存放顶点结点的先后顺序不同,或者边结点的链接次序不同,在按照某种方式遍历图时,将会影响到顶点被访问的先后顺序,即经过遍历得到的遍历序列有可能不同。即使存储结构确定,如果指定的出发顶点不同,遍历得到的结果也会有差别。当然,对于某种已经确定的存储结构与指定的出发顶点,按照某种遍历方法得到的遍历结果则是唯一的。
深度优先搜索
遍历原则:从图中某一指定顶点v出发,先访问v,然后从该顶点的未被访问过的邻接顶点w出发进行深度优先搜索,直到图中与v相通的所有顶点都被访问(此时完成了对图中一个连通分量的遍历)。若图中还存在未被访问过的顶点,则从另一个未被访问过的顶点出发重复上述过程,直到图中所有顶点都被访问。
广度优先搜索
遍历原则: 从图中指定顶点v出发,访问v以后再依次访问v的各个未被访问过的邻接点;然后从这些邻接点出发,按照同样原则依次访问它们的未被访问过的邻接点……,直到图中所有访问过的顶点的邻接点都被访问。若此时图中还存在未被访问过的顶点,则从另一个未被访问过的顶点出发继续进行上述过程,直到图中所有顶点都被访问。
广度优先搜索与深度优先搜索不同,它首先访问指定出发顶点,然后依次访问该顶点的所有未被访问过的邻接点,再接下来访问邻接点的未被访问过的邻接点,依次类推。显然,实现这个过程需要设置一个队列结构。
连通分量
如果G为一个无向图,则简单地调用算法 DFS或者BFS,然后再判断图中是否还有尚未被访问过的顶点,就可以断定该图是否连通。通过反复调用DFS(v)或者BFS(v)就可以得到图中各连通分量,其中v是到目前为止尚未被访问过的一个顶点。算法使用了DFS(也可以使用BFS代替DFS,因为这样做,能达到同样的目的,且并不影响算法的时间效率)。另外,假设算法中用到另外一个子算法OUTCOMPONET(),它输出在最近一次调用DFS的过程中访问过的全部顶点以及所有依附于这些顶点的边。