Dijkstra 算法:迷路?交给 Dijkstra,最短路径迎刃而解!

时间:2025年 01月 11日
作者:小蒋聊技术
邮箱:wei_wei10@163.com
微信:wei_wei10
音频:喜马拉雅

        大家好,欢迎来到“小蒋聊技术”!我是你们的技术小助手——小蒋。今天,我要和大家聊聊一个非常实用且有趣的算法——Dijkstra 算法

        大家是不是也有过这样的经历:出门旅行,地图上标着四通八达的道路,可我怎么知道哪条路最短、最快呢?你是不是也曾经遇到过这种困惑——“这条路太长了吧?我能不能走得更快些?”

        好了,今天我就给大家介绍一个聪明的小助手——Dijkstra 算法!它能帮助你解决这个问题,让你在复杂的路网中找到最短的路径。听起来是不是很酷?那就来和我一起深入了解吧!

1. Dijkstra 算法:解锁最短路径的秘密武器

        首先,让我们从一个简单的例子开始。如果你要从你家(假设是图中的 A 点)出发,去一个从没去过的城市(假设是图中的 D 点),而城市之间的道路长短不一。你怎么知道哪条路最短,能让你尽量少走弯路?

        你是不是想到了手机地图?对的,Dijkstra 算法就是我们生活中“导航”的算法——它帮助你从出发点开始,选择一条最短的路径,一步步到达目的地。

2. Dijkstra 算法:每一步都选择最短的路

        Dijkstra 算法的核心思想很简单:每次选择离自己最近的城市(或者节点),然后继续向前走,直到你遍历到所有城市。这就像你在玩超级玛丽游戏,每一次你选择走的路线都是最短、最快的,直到你打败所有的敌人,走到最终胜利——到达目的地。

Dijkstra 算法的步骤:

  • 初始化:从起点出发,将所有城市的距离初始化为无穷大,只有起点的距离为 0。
  • 选择最近的城市:从已遍历的城市中选择一个距离最小的城市,标记为已遍历。
  • 更新距离:根据当前城市更新与其他城市之间的最短路径。
  • 重复:直到所有城市都被遍历完,得到从起点到所有其他城市的最短路径。

3. Dijkstra 算法的示例:从家到目的地

        为了让大家更清楚地理解,让我们用一个简单的图来说明如何使用 Dijkstra 算法

        假设我们有以下的城市和道路图:

        假设你从城市 A 出发,目标是找到到达城市 D 的最短路径。

Dijkstra 算法过程:

  • 初始化:将所有城市的距离初始化为无穷大,起点城市 A 的距离设为 0。
城市A城市B城市C城市D
0

  • 选择城市 A,更新它的邻居城市(B 和 C)的最短路径。
    • 从 A 到 B 距离是 10,更新 B 的距离为 10。
    • 从 A 到 C 距离是 5,更新 C 的距离为 5。
城市A城市B城市C城市D
0105

  • 选择城市 C,更新它的邻居城市(B 和 D)的最短路径。
    • 从 C 到 B 的距离是 2,加上 A 到 C 的距离 5,总共是 7,更新 B 的距离为 7。
    • 从 C 到 D 的距离是 10,加上 A 到 C 的距离 5,总共是 15,更新 D 的距离为 15。
城市A城市B城市C城市D
07515

  • 选择城市 B,更新它的邻居城市(D)的最短路径。
    • 从 B 到 D 的距离是 20,加上 A 到 B 的距离 7,总共是 27,但是 D 的当前距离是 15,所以不更新。
城市A城市B城市C城市D
07515

  • 选择城市 D,所有城市都已遍历完,最终得到最短路径15。

4. Dijkstra 算法的代码实现:

        好了,听了这么多,大家是不是迫不及待想看看如何将这个算法转化成代码了呢?这里是一个简单的 Java 实现:

import java.util.*;

class Dijkstra {
    public void findShortestPath(Graph graph, int source) {
        int[] dist = new int[graph.size()];
        Arrays.fill(dist, Integer.MAX_VALUE);
        dist[source] = 0;

        PriorityQueue<Node> pq = new PriorityQueue<>(Comparator.comparingInt(n -> n.distance));
        pq.add(new Node(source, 0));

        while (!pq.isEmpty()) {
            Node node = pq.poll();
            for (Edge edge : graph.getEdges(node)) {
                if (dist[edge.to] > dist[node.id] + edge.weight) {
                    dist[edge.to] = dist[node.id] + edge.weight;
                    pq.add(new Node(edge.to, dist[edge.to]));
                }
            }
        }
    }
}

解释代码:

        这段代码实现了 Dijkstra 算法,使用了 优先队列 来保证每次都选择最短路径。它通过更新每个节点的最短路径,最终输出从起点到其他所有节点的最短路径。

5. Dijkstra 与其他算法的对比

        Dijkstra 算法虽然很强大,但它的应用场景是 单源最短路径。也就是说,它只关心从一个起点到其他所有点的最短路径。如果你需要计算 所有点对之间的最短路径,那么就需要使用 Floyd-Warshall 算法

  • Dijkstra 是单源最短路径,逐步更新距离。
  • Floyd-Warshall 是所有点对之间的最短路径,一次性计算所有的路径。

6. 总结

        今天我们学习了 Dijkstra 算法,它是一种高效的 单源最短路径算法。通过每次选择最短的路径,Dijkstra 算法帮助我们找到从一个点到其他所有点的最短路径,避免了冤枉路。

        但这里有一个问题:我们知道 A 到 D 的最短距离是 15,假设起点是 A,终点是 D,但如何找到从 A 到 D 的具体路径呢?

        这个问题我将在下一期为大家解答!敬请期待哦~

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

小蒋聊技术

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值