数据类型
有向图的表示
我们使用邻接表来表示有向图,其中边v->w表示为顶点v所对应的邻接链表中包含一个w顶点,与无向图的区别是,每条边都只会出现一次。
有向图的取反
利用有向图的取反可以找出“指向”每个顶点的所有边。
和无向图的区别
在用邻接表表示无向图时,如果v在w的链表中,那么w必然也在v的链表中。但在有向图中这种对称性是不存在的。这个区别在有向图的处理中影响深远。
有向图中的可达性
- 单点可达性。给定一幅有向图和一个起点s,是否存在一条从s到达给定顶点v的有向路径。
- 多点可达性。给定一幅有向图和顶点的集合,是否存在一条从集合中的任意顶点到达给定顶点v的邮箱路径。
使用深度优先搜索解决:
public class DirectedDFS {
private boolean[] marked;
DirectedDFS(DiGraph G, int s){
marked = new boolean[G.V()];
dfs(G, s);
}
DirectedDFS(DiGraph G, Iterable<Integer> sources){
marked = new boolean[G.V()];
for(int v : sources){
if(!marked[v]){
dfs(G, v);
}
}
}
private void dfs(DiGraph G, int v){
marked[v] = true;
for(int w : G.adj(v)){
if(!marked[w]){
dfs(G, w);
}
}
}
public boolean marked(int v){
return marked[v];
}
}
有向图的寻路
- 单点有向路径
- 单点最短有向路径
有向图中环的检测
我们使用深度优先搜索来解决这个问题。一旦我们找到了一条有向边v->w且w已经存在于栈中,就找到了一个环,因为栈表示的是一条由w到v的有向路径,而v->w正好补全了这个环。同时,如果没有找到这样的边,那就意味着这幅有向图是无环的。
import java.util.Stack;
public class DirectedCycle {
private boolean[] marked;
pri