Dijkstra模板详解(适合完全不懂的小白)

最近我在写算法题时在dijkstra上卡了很久,所谓dijkstra算法,主要针对最短路径的算法题,准确来说,是针对单源最短路径,而什么是单源最短路径呢?

单源最短路径:就是从某个起点开始,到其他任一点的最短路径。与之相对的是多元最短路径,他是求任一点到任一点的最短路径,这个对应的是floyd算法,而今天要说的是dijkstra算法,接下来,从一道模板题开始,让我细细道来。

dijkstra算法,就是不断迭代当前最优解的贪心算法,每次从可选节点中选距离起点最短的点,然后不断更新所有点的最短路径值,直到所有节点都遍历。

Dijkstra算法的实现步骤如下:

  1. 初始化距离数组dist,将起始节点的距离设为0,其它节点的距离设为无穷大。初始化标记数组st,表示节点是否已经确定最短路径。

  2. 选择距离起始节点最近的一个节点t,将其标记为已确定最短路径。

  3. 遍历所有未确定最短路径的节点j,如果从起始节点到已确定最短路径的节点t再到j节点的距离比当前dist[j]的值更小,则更新dist[j]的值。

  4. 重复2、3步骤,直到所有节点的最短路径长度被确定。

最终,可以得到起始节点到所有节点的最短路径长度,如果某个节点的最短路径长度为无穷大,则表示起始节点无法到达该节点。

需要注意的是,Dijkstra算法只适用于没有负权边的图。如果图中存在负权边,则需要使用其他算法,如Bellman-Ford算法或SPFA算法。

这个是acwing的一道模板题。

在看算法代码时,大家应该跟我一样存在一个疑惑,为什么这样写就能怎么样怎么样,接下来我详细说一下这个模板,这个代码是基于c++写的,即使没有学过,应该也不难理解,毕竟跟c语言很相似。

int g[N][N]; //用于存放从某个点到某个点的距离,这个用于后面存放输入的从x到y的距离
int dist[N];//存放从起点到其他点的最短路径
bool st[N];//用于判断某点是否被使用过了,假如st[1]=true,表示1这个节点被用过了                       int n,m //这个是题目需要的参数

然后我们到主函数memset(g, 0x3f, sizeof g),这一句是将g,也就是上面的g[N][N]初始化为0x3f表示无穷大,并没有什么特殊意义,只是在写这类题时所形成的习惯。

memset(g, 0x3f, sizeof g)将g这个数组的每个字节来设置为0x3f,因为整形4个字节,所以一个元素的大小为0x3f3f3f3f(0x代表十六进制)

也就是说这里我们先初始化为无穷大,然后记录x到y的距离,然后就是调用自定义dis函数,第一步也是进行一个初始化的操作,初始化dist。然后将dist[1]赋值为1,因为题目的起点是1,如果起点是其他的,在这里将下标换一下即可。

然后就是进行一个循环,从0到n,循环n次,是为了找出n个节点,每次找一个,每次都初始化t=-1;这里用t来作为后面for循环的一个判断条件,因为后面for循环中当第一个进入判断时,t作为当前的在所有最短路径中最短的,然后不断更新,找到最后,就找到了,从起点到任一点的最短距离中最短的,然后st[t]=true,表示已经拿出来用过了,后面一个for循环应该很好理解,就是更新所有从起点到任一点的最短距离,因为,你找到了起点到t距离最短,那其他点经由t作为中转点,就能算出从起点到任一点的最短距离的另一结果,再跟原本的比较,取消的,循环n次,最后就是所要求的。

if (dist[n] == 0x3f3f3f3f) return -1;这个判断应该也很好理解,前面已经讲过被memset初始化的值。

这个模板只能套用模板题,其他还有挺多不同变种的题,不一定可套用。

如果看完还有什么不懂的地方,请发的评论区,我会一一回复,如果我有什么讲的不对的地方,也可以提出来,大家共同进步。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
Dijkstra算法是一种用于图形数据结构的贪心算法,用于查找两个节点之间的最短路径。它被广泛用于路由算法和网络协议中。 Dijkstra算法的基本思想是从起点开始,每次找到距离起点最近的一个节点,然后以该节点作为中转点,更新其他所有节点的距离。这个过程不断重复,直到所有节点的距离都被确定为止。 具体实现过程如下: 1. 初始化所有节点的距离为无穷大,起点的距离为0。 2. 选取起点作为当前节点。 3. 对于当前节点,计算它到所有邻居节点的距离,并更新邻居节点的距离。 4. 标记当前节点为已访问。 5. 从未访问的节点中选取距离起点最近的节点作为下一个当前节点。 6. 重复步骤3-5,直到所有节点都被访问过。 最终得到的每个节点的距离就是它到起点的最短距离。 要注意的是,Dijkstra算法只适用于有权重的图,而且不能处理负权重的情况。如果有负权重的情况,需要使用另一种算法,如Bellman-Ford算法。 另外,Dijkstra算法可以用优先队列来优化,以减少计算量。具体实现方法是将节点按照距离从小到大排序,并使用优先队列来选取距离最小的节点。这样可以避免遍历所有节点来选取距离最小的节点,从而提高算法效率。 总之,Dijkstra算法是一种高效的求解最短路径的算法,可以应用于很多领域,如路由算法、网络协议、地图导航等。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值