public static void PrintPathLoop(int[] last, AdjacencyList adj, int endVertexID) { if (last[endVertexID - 1] != -1) { PrintPathLoop(last, adj, last[endVertexID - 1] + 1); Console.Write("->"); } Console.Write(adj.Find(endVertexID).data.GetVertexName()); }
public static void PrintPath(int[] last, double[] dist, AdjacencyList adj, int startVertexID) { double inf = Convert.ToDouble(int.MaxValue); int n = adj.items.Count(); for (int i = 0; i < n; i++) { if (i != startVertexID - 1) { if (last[i] == -1 || dist[i] == 0) { Console.WriteLine("[{0} ==> {1}] : {2}", adj.Find(startVertexID).data.GetVertexName(), adj.Find(i + 1).data.GetVertexName(), "No Path!"); } else { Console.Write("[{0} ==> {1}] : {2}\t", adj.Find(startVertexID).data.GetVertexName(), adj.Find(i + 1).data.GetVertexName(), dist[i]); PrintPathLoop(last, adj, i + 1); Console.WriteLine(); } } } }
//string path = string.Empty; public static void DijkstraShortestPath(AdjacencyList adj, int capacity, AdjacencyList.VertexData startVerData, AdjacencyList.VertexData endVerData) { double[] dist = new double[1000]; double inf = Convert.ToDouble(int.MaxValue); double min; int n; int u = 0; //string s = string.Empty; //搜寻开始结点、终止结点名对应的结点 AdjacencyList.Vertex startVer = null; AdjacencyList.Vertex endVer = null; startVer = adj.Find(startVerData); endVer = adj.Find(endVerData); //Console.WriteLine("{0}{1}",startVer.data.GetVertexName().ToString(),startVer.data.GetVertexID().ToString()); //Console.WriteLine("{0}{1}",endVer.data.GetVertexName().ToString(),endVer.data.GetVertexID().ToString()); //校验adj顶点数是否和capacity一致 n = adj.items.Count(); if (n != capacity) { throw new ArgumentException("图顶点数与传入顶点数不一致!"); } int[] last = new int[n];//存储最短路径,每个结点的上一个结点 //初始化dist数组 for (int i = 0; i < n; i++) { dist[i] = inf; } //初始化路径表 for (int i = 0; i < n; i++) { last[i] = startVerData.GetVertexID() - 1; //vertexData id从1开始,作为数组下标要减去1 } last[startVerData.GetVertexID() - 1] = -1; dist[startVer.data.GetVertexID() - 1] = 0; startVer.visited = true; //将开始结点设为已访问 AdjacencyList.Node tmpNode = startVer.firstEdge; if (tmpNode != null) { while (tmpNode != null) { dist[tmpNode.adjvex.data.GetVertexID() - 1] = tmpNode.weight; tmpNode = tmpNode.next; } } //第一个点(初始点已装载完毕) //遍历结点,计算最短路径 AdjacencyList.Vertex tmpVertex = null; for (int i = 0; i < n - 1; i++) { min = inf; //找到离StartVer结点最近的点 foreach (AdjacencyList.Vertex v in adj.items) { if (v.visited == false) { int j = v.data.GetVertexID() - 1; if (dist[j] < min && dist[j] != 0) { min = dist[j]; tmpVertex = v; u = j; } } } if (tmpVertex != null) { tmpVertex.visited = true; if (tmpVertex.firstEdge != null) { do { int vv = tmpVertex.firstEdge.adjvex.data.GetVertexID() - 1; if (tmpVertex.firstEdge.weight != 0 && tmpVertex.firstEdge.weight < inf && tmpVertex.firstEdge.adjvex.visited == false) { if (min + tmpVertex.firstEdge.weight < dist[vv]) { dist[vv] = min + tmpVertex.firstEdge.weight; last[vv] = u; } } tmpVertex.firstEdge = tmpVertex.firstEdge.next; } while (tmpVertex.firstEdge != null); } } } foreach (AdjacencyList.Vertex a in adj.items) { Console.WriteLine(a.visited); } for (int i = 0; i < capacity; i++) { Console.WriteLine("{0},{1}", dist[i], last[i]); } PrintPath(last, dist, adj, startVerData.GetVertexID()); Console.ReadKey(); }
static void Main(string[] args) { //获取配置文件顶点数 int VertexNum = Convert.ToInt32(System.Configuration.ConfigurationManager.AppSettings["VertexNum"]); //Vertex配置文件保存顶点信息,格式为 "(顶点名,顶点id)|(顶点名,顶点id)|...|" string VertexDataString = System.Configuration.ConfigurationManager.AppSettings["VertexData"]; AdjacencyList a = new AdjacencyList(VertexNum); string[] strArray = VertexDataString.Split('|'); foreach (string k in strArray) { string x = k.Trim('(').Trim(')'); //去掉左右小括号 //分割顶点的名称和id int pos = x.IndexOf(','); if (pos < 0) { break; } AdjacencyList.VertexData v = new AdjacencyList.VertexData(x.Substring(0, pos), Convert.ToInt32(x.Substring(pos + 1))); //Console.WriteLine("{0}{1}",v.GetVertexName(),v.GetVertexID()); //添加顶点 a.AddVertex(v); } //由配置文件获取加权有向图边的关系,格式暂时为 "(顶点名1,顶点名2,权值,是否是单向)|(顶点名1,顶点名2,权值,是否是单向)|...|" string EdgeString = System.Configuration.ConfigurationManager.AppSettings["Edge"]; strArray = EdgeString.Split('|'); foreach (string k in strArray) { string x = k.Trim('(').Trim(')'); int pos = 0; pos = x.IndexOf(','); if (pos < 0) { break; } AdjacencyList.VertexData VertexData1 = a.Find(x.Substring(0, pos)).data; x = x.Remove(0, pos + 1); pos = x.IndexOf(','); AdjacencyList.VertexData VertexData2 = a.Find(x.Substring(0, pos)).data; x = x.Remove(0, pos + 1); pos = x.IndexOf(','); double weight = Convert.ToDouble(x.Substring(0, pos)); x = x.Remove(0, pos + 1); bool isDirected; if (x == "T") { isDirected = true; } else if (x == "F") { isDirected = false; } else { throw new ArgumentException("无效的方向标识!"); } //添加边 a.AddEdge(VertexData1, VertexData2, weight, isDirected); } //Console.WriteLine(ConString); //添加顶点 //AdjacencyList.VertexData A = new AdjacencyList.VertexData("A", 1); //AdjacencyList.VertexData B = new AdjacencyList.VertexData("B", 2); //AdjacencyList.VertexData C = new AdjacencyList.VertexData("C", 3); //AdjacencyList.VertexData D = new AdjacencyList.VertexData("D", 4); //AdjacencyList.VertexData E = new AdjacencyList.VertexData("E", 5); //AdjacencyList.VertexData F = new AdjacencyList.VertexData("F", 6); //a.AddVertex(A); //a.AddVertex(B); //a.AddVertex(C); //a.AddVertex(D); //a.AddVertex(E); //a.AddVertex(F); //添加边 //a.AddEdge(A, B, 3, true); //a.AddEdge(A, C, 10, true); //a.AddEdge(C, F, 5, true); //a.AddEdge(B, D, 2, true); //a.AddEdge(D, E, 4, true); //a.AddEdge(E, C, 2, true); //a.AddEdge(E, F, 7, true); Console.WriteLine(a.ToString()); Console.ReadKey(); string StartVertexName = System.Configuration.ConfigurationManager.AppSettings["StartVertexName"]; string EndVertexName = System.Configuration.ConfigurationManager.AppSettings["EndVertexName"]; RouteDijkstra.DijkstraShortestPath(a, VertexNum, a.Find(StartVertexName).data, a.Find(EndVertexName).data); }