package com.renhui.graph;
import java.util.Stack;
/**
* 深度优先搜索 路径查找(无向图)
*/
public class DepthFirstPath {
private boolean[] marked; //索引代表顶点,值表示当前顶点是否已经被搜索
private int s; // 起点
private int[] edgeTo; // 索引代表顶带你,值代表从起点s到当前顶带你路径上的最后一个顶点
// 使用深度优先搜索对象,找出G图中起点为s的所有路径
private DepthFirstPath(Graph g, int s) {
this.marked = new boolean[g.V()];
this.s = s;
this.edgeTo = new int[g.V()];
dfs(g, s);
}
private void dfs(Graph g, int v) {
marked[v] = true;
for (Integer w : g.adj(v)) {
if (!marked[w]) {
edgeTo[w] = v; // 到达顶点w的路径上的最后一个顶点是v
dfs(g, w);
}
}
}
// 顶点s和顶点v之间是否存在路径
public boolean hasPathTo(int v) {
return marked[v];
}
// 输出起点s到顶点v之间的路径(就是该路径经过的顶点)
public Stack<Integer> pathTo(int v) {
if (!hasPathTo(v)) {
return null;
}
Stack<Integer> pathStack = new Stack<>();
// 通过循环,从顶点v开始,一直往前找,直到找到起点为止
for (int x = v; x != s; x = edgeTo[x]) {
pathStack.push(x);
}
// 最后把起点放入到栈中
pathStack.push(s);
return pathStack;
}
public static void main(String[] args) {
// 准备一幅图
Graph graph = new Graph(13);
graph.addEdge(0, 5);
graph.addEdge(0, 1);
graph.addEdge(0, 2);
graph.addEdge(0, 6);
graph.addEdge(5, 3);
graph.addEdge(5, 4);
graph.addEdge(3, 4);
graph.addEdge(4, 6);
graph.addEdge(7, 8);
graph.addEdge(9, 11);
graph.addEdge(9, 10);
graph.addEdge(9, 12);
graph.addEdge(11, 12);
// 准备深度优先搜索对象
DepthFirstPath depthFirstPath = new DepthFirstPath(graph, 0);
Stack<Integer> result = depthFirstPath.pathTo(3);
while (!result.empty()) {
System.out.println(result.pop());
}
}
}