import java.util.ArrayList;
import java.util.Collections;
public class SingleSourcePath
{
private Graph G;
private int s;
private boolean [] visited;
private int [] pre;
public SingleSourcePath(Graph G,int s)//由于是要解决单源路径问题
{//所以要传入具体以哪个顶点为原点的参数 int s
G.validateVertex(s);
this.G=G;
this.s=s;
visited=new boolean[G.V()];
pre=new int[G.V()];//用于存储最短路径
for(int i=0;i<pre.length;i++)
{
pre[i]=-1;
}
dfs(s,s);//默认将某一个源作为自己,这是约定俗成的方式
}
private void dfs(int v,int parent)//将v的按照dfs顺序遍历的上一个顶点叫做parent
{
visited[v]=true;
pre[v]=parent;
for(int w:G.adj(v))//访问节点v的邻接节点并对其进行dfs操作
{
if(!visited[w])//如果w没有被遍历过
{
dfs(w,v);
}
}
}
public boolean isConnectedTo(int t)//用来判断从源节点到目的节点t是否是可达的
{
G.validateVertex(t);
return visited[t]==true;//这里只需要判断在进行深度优先遍历的时候该节点是否被访问过
}
public Iterable<Integer> path(int t)//返回一个迭代器
{
ArrayList<Integer> res=new ArrayList<>();
if(!isConnectedTo(t))
{
return res;//这种情况是:source到目的节点没有路径
//返回的必定是空值
}
int cur=t;//用于逆向寻找路径
while(cur!=s)
{
res.add(cur);
cur=pre[cur];
}
res.add(s);//注意此时所存储的路径是倒序的
Collections.reverse(res);//使用Collection工具类中的reverse函数将原本逆序的路径正过来
return res;
}
public static void main(String[] args)//测试函数
{
Graph g=new Graph("g.txt");
SingleSourcePath ssPath=new SingleSourcePath(g, 0);
System.out.println("0->6"+ssPath.path(6));
System.out.println("0->5"+ssPath.path(5));
System.out.println("0->4"+ssPath.path(4));
System.out.println("0->3"+ssPath.path(3));
System.out.println("0->2"+ssPath.path(2));
System.out.println("0->1"+ssPath.path(1));
System.out.println("0->0"+ssPath.path(0));
}
}
008.利用深度优先搜索,判断两个节点是否连通,并且返回他们之间的路径
最新推荐文章于 2023-06-28 08:45:41 发布