题目:

  最短路:给定两个顶点,在以这两个点为起点和终点的路径中,边的权值和最小的路径。考虑权值为点之间的距离。

  单源最短路问题,Bellman-ford算法

  思路:每次循环检查所有边,可优化。

  应用于旅游等路径最小问题。

代码:

 import java.util.Arrays;

 public class 图的最短路问题_单源 {
public static void main(String[] args) {
int[] shortestPath = shortestPath(0);
System.out.println(Arrays.toString(shortestPath));
// 输出[0, 2, 5, 7, 11, 8, 16]
} /**
* 求起点到各顶点的最短距离
*
* @param s 起点
* @return
*/
private static int[] shortestPath(int s) {
int n = graph.length;
// 记录s到各顶点的最短距离
int[] d = new int[n];
for (int i = 0; i < n; i++) {
d[i] = Integer.MAX_VALUE;
}
d[s] = 0;// 到自己的距离为0
while (true) {
boolean update = false;
// 扫描所有的边
for (int i = 0; i < n; i++) {
// 起点到i的最短距离还没算出来
if (d[i] == Integer.MAX_VALUE)
continue;
for (int j = 0; j < n; j++) {
int cost = graph[i][j]; // i,j之间的距离
if (cost > 0) { // i,j 两点之间有边,起点是i
if (d[j] > d[i] + cost) { // 起点先到i,i->j
// 两端距离加起来比起点直接到j的距离短,则更新
update = true;
d[j] = d[i] + cost;
}
}
}
}
// 无需任何更新,退出外循环
if (!update)
break;
}
return d;
} static int[][] graph = {
{ 0, 2, 5, 0, 0, 0, 0 },
{ 2, 0, 4, 6, 10, 0, 0 },
{ 5, 4, 0, 2, 0, 0, 0 },
{ 0, 6, 2, 0, 0, 1, 0 },
{ 0, 10, 0, 0, 0, 3, 5 },
{ 0, 0, 0, 1, 3, 0, 9 },
{ 0, 0, 0, 0, 5, 9, 0 }
};
}

  对于上一个代码。可以先把边集提取出来,这样不用每次扫描二维数组。

   Edge类:

 /**
* 边 的封装
* 边集可以用来表示图
*/
public class Edge<T> implements Comparable<Edge> {
private T start;
private T end;
private int distance; public Edge(T start, T end, int distance) {
this.start = start;
this.end = end;
this.distance = distance;
} public T getStart() {
return start;
} public void setStart(T start) {
this.start = start;
} public T getEnd() {
return end;
} public void setEnd(T end) {
this.end = end;
} public int getDistance() {
return distance;
} public void setDistance(int distance) {
this.distance = distance;
} @Override
public String toString() {
return start + "->" + end + ":" + distance;
} @Override
public int compareTo(Edge obj) {
int targetDis = obj.getDistance();
return distance > targetDis ? 1 : (distance == targetDis ? 0 : -1);
}
}

  优化过后的代码:

 import java.util.ArrayList;
import java.util.Arrays;
import java.util.List; public class 图的最短路问题_优化_边集 {
public static void main(String[] args) {
edges = buildEdges(graph);
int[] shortestPath = shortestPath(0);
System.out.println(Arrays.toString(shortestPath));
// 输出[0, 2, 5, 7, 11, 8, 16]
} /**
* 求起点到各顶点的最短距离
*
* @param s
* 起点
* @return
*/
private static int[] shortestPath(int s) {
int n = graph.length;
// 记录s到各顶点的最短距离
int[] d = new int[n];
for (int i = 0; i < n; i++) {
d[i] = Integer.MAX_VALUE;
}
d[s] = 0;// 到自己的距离为0
while (true) {
boolean update = false; for (Edge<Integer> e : edges) {
if (d[e.getStart()] != Integer.MAX_VALUE && d[e.getEnd()] > d[e.getStart()] + e.getDistance()) {
update = true;
d[e.getEnd()] = d[e.getStart()] + e.getDistance();
}
} if (!update)
break;
}
return d;
} static List<Edge<Integer>> edges; static List<Edge<Integer>> buildEdges(int[][] graph) {
int n = graph.length;
List<Edge<Integer>> edges = new ArrayList<>();
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
int cost = graph[i][j]; // i,j之间的距离
if (cost > 0) { // i,j 两点之间有边,起点是i
edges.add(new Edge<>(i, j, cost));
}
}
}
return edges;
} static int[][] graph = {
{ 0, 2, 5, 0, 0, 0, 0 },
{ 2, 0, 4, 6, 10, 0, 0 },
{ 5, 4, 0, 2, 0, 0, 0 },
{ 0, 6, 2, 0, 0, 1, 0 },
{ 0, 10, 0, 0, 0, 3, 5 },
{ 0, 0, 0, 1, 3, 0, 9 },
{ 0, 0, 0, 0, 5, 9, 0 }
};
}

最新文章

  1. linux中inode、软链接、硬链接
  2. tornado 学习笔记5 构建Tornado网站应用
  3. java 的SYSTEM类【转】
  4. golang处理错误的艺术
  5. POJ 2226 Muddy Fields (最小点覆盖集,对比POJ 3041)
  6. Hadoop学习总结之五:Hadoop的运行痕迹
  7. Part 92 Significance of Thread Join and Thread IsAlive functions
  8. oracle 日志学习(转载)
  9. 流形(Manifold)初步【转】
  10. show_space.sql.txt
  11. PAT乙级练习1001
  12. UIEvent&amp;nbsp;UIResponder&amp;nbsp;UI_04
  13. Maven入门教程(一)
  14. 转导推理——Transductive Learning
  15. Django-rest-framework 接口实现 认证:(auth | authentication)
  16. (转载)C#使用MemoryStream类读写内存
  17. Java中Access restriction:&#183;&#183;&#183;&#183;的解决方法
  18. Python 语法糖装饰器的应用
  19. 启动项目报错:502 Server dropped connection The following error occurred while trying to access http://localhost:8080/TestDemo:
  20. (译)我为什么用Go语言来做区块链——Syed Jafar Naqvi——Co-Founder/CEO at Karachain

热门文章

  1. JQUERY获取loaded 宽高这么变态
  2. 使用XAMPP和DVWA在Windows7上搭建渗透测试环境
  3. pycharm跨目录调用文件
  4. DD XOFT虚拟键盘鼠标
  5. Instrumentation(3)
  6. Elasticsearch笔记二之Curl工具基本操作
  7. 【费马小定理】BZOJ3260 跳
  8. C#多线程中的异常处理
  9. DCGAN 代码简单解读
  10. TensorFlow从1到2(九)迁移学习