java 迪杰斯特拉_Java实现 迪杰斯特拉 dijkstra 算… | 学步园

求单源最短路径的经典

2. 从V-S中选取这样一个顶点w: 满足经过S集合中任意顶点 v到w 的路径最短, 即

满足( 源到v的路径 + v到w的路径) 最小的那个w. 其中v 属于S, w属于S-V。将w 加入S, 并从V-S中移除w.

3. 如此反复,直到V-S变空集为止。

归纳基点:

比如开始 S中只有原点s, 那我们从V-S中选取离s最近的点w, 则s直接到w的路径一定最短。因为如果存在另一个点w2, 使得

s->w2->w 的路径比s

直接到w短,那么s->w2 一定 小于s->w, 那么

w就不是离s最近的点,与我们选取的w离s最近这个先前条件矛盾。所以在最开始,选出来的那个点 w

一定确定了最短路径,即s->w 的边长。 w已经确定,将w加入S.

2. 此时S中有 v1,v2....vk 顶点,V-S中剩下 w1,w2.....Wn-k

顶点。我们此时当然选择离S集合最近的点w.

w必然满足 D[w]= Min(D[v]+D[v to

w]) 其中 D[x]

表示从原点到x的最短路径长。

这个w 此时一定取得了最短路径D[w], 因为如果有其他的路径,假设是

S集合某路径->Wi->w, 那么就应当去选取Wi 做为该点而不是w.

因为 S集合某路径长D[v] + D[v to Wi] < D[v]+D[v to w] 与

w满足的公式矛盾。

因此w必然是最小的。将w加入 S集合。

3. 实现框架+核心代码:

采用邻接表存储图

1

4 public class Edge {

5 public Vertex dest;//目标顶点

6 public double cost;//代价

7

8 public Edge(Vertex d,double c){

9 dest=d;

10 cost=c;

11 }

12 }

13

顶点类:

1 public class Vertex implements

Comparable{

2 public String name;//顶点名

3 public List adj;//邻接表

4 public double dist;// 从原点到该点的最短路径长

5 public Vertex prev;//最短路径前一个节点

6 public int scratch;//算法需要

7 public boolean visited;

8 public Vertex(String nm){

9 name=nm;

10 adj=new ArrayList();

11 reset();

12 }

13 public void reset(){

14 visited=false;

15 dist=Graph.INFINITY;

16 prev=null;

17 scratch=0;

18 }

19 @Override

20 public int compareTo(Vertex o) {

21 double c=o.dist;

22 return distc?1:0;

23 }

24 }

25

1

9 public void dijkstraSlow(String startName){

10 PriorityQueue pq=new

PriorityQueue();

11 Vertex start=vertexMap.get(startName);

12 if(start==null)

13 throw new IllegalArgumentException("Hey fk,start vertex is

illegal!");

14 clearAll();

15 //pq.add(start);

16 start.dist=0;

17 //构造V-S集合,将顶点全部装入优先级队列(V-S集合).

18 //优先级队列的队首元素即离原点最近的,因为Vertex对象的比较器是

19 //根据Vertex对象到原点的距离来比较的。

20 //其实这里可以进一步优化的,由于开始选中加入S的必定是原点,

21 //且只有刚加入S的顶点的邻接顶点才有可能是新的加入S的顶点,

22 //所以开始只要把原点放入vertexMap即可,第一次将原点加入S,

23 //然后更新其邻接点到原点的距离.从中选出最小的来加入S。

24 //这里为了保持算法清晰,没有进行优化.

25 for(Vertex v:vertexMap.values())

26 pq.add(v);

27

28

29 int seenNum=0;

30 while(!pq.isEmpty()&&seenNum

31

32 Vertex v=pq.remove();//第一次取的是原点,其余情况自然是到原点最近的点.

33

34 if(v.scratch!=0)//如果v已经加入了S,则跳过

35

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
迪杰斯特拉法(Dijkstra's algorithm)是一种用于解决带权图中最短路径问题的法。它以起始点为中心,逐层向外扩展,直到扩展到终点为止。以下是Java实现迪杰斯特拉法的示例代码: ```java import java.util.*; public class DijkstraAlgorithm { private static final int INF = Integer.MAX_VALUE; // 无穷大 public static void dijkstra(int[][] graph, int start) { int n = graph.length; // 图的顶点数 int[] dist = new int[n]; // 存储起始点到各个顶点的最短距离 boolean[] visited = new boolean[n]; // 记录顶点是否已被访问 // 初始化dist数组,默认为无穷大 Arrays.fill(dist, INF); dist[start] = 0; // 起始点到自身的距离为0 for (int i = 0; i < n - 1; i++) { int minDist = INF; int minIndex = -1; // 找到当前未访问的顶点中距离起始点最近的顶点 for (int j = 0; j < n; j++) { if (!visited[j] && dist[j] < minDist) { minDist = dist[j]; minIndex = j; } } if (minIndex == -1) { break; // 所有顶点都已访问过,退出循环 } visited[minIndex] = true; // 标记该顶点为已访问 // 更新与当前顶点相邻的顶点的最短距离 for (int j = 0; j < n; j++) { if (!visited[j] && graph[minIndex][j] != INF && dist[minIndex] + graph[minIndex][j] < dist[j]) { dist[j] = dist[minIndex] + graph[minIndex][j]; } } } // 输出起始点到各个顶点的最短距离 for (int i = 0; i < n; i++) { System.out.println("从起始点到顶点 " + i + " 的最短距离为:" + dist[i]); } } public static void main(String[] args) { int[][] graph = { {0, 2, 4, INF, INF}, {2, 0, 1, 4, 2}, {4, 1, 0, 1, 3}, {INF, 4, 1, 0, 1}, {INF, 2, 3, 1, 0} }; int start = 0; // 起始点的索引 dijkstra(graph, start); } } ``` 这段代码实现迪杰斯特拉法,通过传入一个带权图的邻接矩阵和起始点的索引,计出起始点到各个顶点的最短距离,并输出结果。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值