首页 > 编程语言 >经典算法——最短路径(Floyd+Dijkstra)

经典算法——最短路径(Floyd+Dijkstra)

时间:2022-12-01 00:35:14浏览次数:58  
标签:cnt int ed 算法 最短 Dijkstra Floyd include dis

Floyd

时间复杂度:O(n^3)
简介:作为最短路算法中复杂度最高的算法没有之一,标志性结构三层循环,核心结构本质DP思想具 有动态规划的无后效性

他真的没有优点啦?!不,他有!

虽然SPFA,Dijkstra比他跑得快,但是只能算一个点到任意一点的最短路径,可Floyd是解决多源最短路的最佳方法,他能计算任意两点之间的最短距离

if(d[i][j]>d[i][k]+d[k][j])
	d[i][j]=d[i][k]+d[k][j]

想必这个代码我们在这个算法里并不陌生
设:总共有n个节点
我们在寻找的任意两点之间最短路时在中转点k我们为何能够确定下这个k点,是因为我们由三层循环已经判断了在这个点k前的路径是最短的,所运用的方法是O(n^2)的松弛
DP的无后效性,体现在k不仅是中转点还是一个状态变量,在选中k点前k已经作为i或j进行枚举了,所以说每次在确定下一个点的时候我们都保证了在1到k之间已经是最优路径
实现代码如下:

for(int k=1;k<=n;k++)
	for(int i=1;i<=n;i++)
		for(int j=1;j<=n;j++)
			if(d[i][j]>d[i][k]+d[k][j])
				d[i][j]=d[i][k]+d[k][j];

Dijkstra

时间复杂度:O(n^3)
简介:利用的思想是贪心思想,准备阶段为将起点到各个点的距离都统计出来,核心阶段松弛遍历过的点,看是否能够作为中转点使其起点到另一个点的距离更短
借用大佬的图举个例子
enter image description here
我们要想计算出1号点到各个点的最短路径
第一步
enter image description here
我们将两相邻点的距离进行统计
第二步
将1到各点的距离用一个dis数组进行储存,不能直接到达的用∞表示
第三步
寻找距离1点最近的点然后将最近的这个点当作中转点,然后重新计算经过该中转点后能够直接到达的点的距离,然后再次寻找此时距离1点最近的点,以此类推最后能确定1点到各个点的最近距离
enter image description here
核心代码实现

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<queue>
using namespace std;
struct edge
{
int u,v,x;
} ed[1000010];
struct node
{
	int x,y;
bool operator <(const node & a)const
{
	return y>a.y;
}
};
priority_queue<node>que;
int head[1000010];
int dis[1000010];
int n,m,s,cnt;
void add(int x,int y,int z)
{
cnt++;
ed[cnt].u=head[x];
ed[cnt].v=y;
ed[cnt].x=z;
head[x]=cnt;
}
void dij()
{
for(int i=1; i<=n; i++)
	dis[i]=2147483647;
dis[s]=0;
que.push((node)
{
	s,0
});
while(!que.empty())
{
	node temp=que.top();
	que.pop();
	int x=temp.x,y=temp.y;
	if(y!=dis[x])
		continue;
	for(int i=head[x]; i; i=ed[i].u)
	{
		if(dis[ed[i].v]>dis[x]+ed[i].x)
		{
			dis[ed[i].v]=dis[x]+ed[i].x;
			que.push((node)
			{
				ed[i].v,dis[ed[i].v]
			});
		}
	}
}
}
int main()
{
cin>>n>>m>>s;
for(int i=1; i<=m; i++)
{
	int x,y,z;
	cin>>x>>y>>z;
	add(x,y,z);
}
dij();
for(int i=1; i<=n; i++)
	cout<<dis[i]<<" ";
return 0;
}

本蒟蒻目前只会这两种算法
至于SPFA和Bellman-Ford还需要努力
敬请期待!

标签:cnt,int,ed,算法,最短,Dijkstra,Floyd,include,dis
From: https://www.cnblogs.com/xmex/p/16940236.html

相关文章

  • 最短路算法及其常见扩展应用
    第一节——最短路问题基本概念:由于无向边可以看作两条相反的有向边,于是我们默然按照有向边的形式讨论存图方式:邻接矩阵:空间复杂度\(O(n^2)\),优点:\(O(1)\)查找\(x->y\)......
  • 最短路径Dijkstra算法
    最短路径最短路径的性质:路径是有向的权重不一定等价于距离,权重也可以指时间,花费或者其他并不是所有顶点都是可达的负权重会使得问题更复杂(Dijkstra算法不适用于......
  • Floyd算法(最短路径)
    Floyd算法允许图中有带负权值的边,但不许有包含带负权值的边组成的回路。     上一篇文章我们通过迪杰斯特拉算法解决了从某个源点到其余各顶点的最短路径问题。从循......
  • 最短路好题整理
    [ABC077D]SmallMultiple题意:给定一个整数\(K\)。求一个\(K\)的正整数倍\(S\),使得\(S\)的数位累加和最小。\(2\leK\le{10}^5\)\(K\)是整数。思路只看题......
  • 拓端tecdat|python编程指导使用马尔可夫决策过程(MDP)动态编程来解决最短路径强化学习
    python中使用马尔可夫决策过程(MDP)动态编程来解决最短路径强化学习问题 在强化学习中,我们有兴趣确定一种最大化获取奖励的策略。假设环境是马尔可......
  • 细分图中的可到达节点 Dijkstra算法Python实现
    题目大意个无向图(原始图)中有n个节点,编号从0到n-1。对每条边增加若干节点构建“细分图”,求解从节点0出发能抵达的不超过距离为maxMove的节点数量。输入:edges=[......
  • 【算法入门&搜索法】走迷宫|单源最短路径1
    文章目录​​......
  • 882. 细分图中的可到达节点 ----- Dijkstra算法、图
    给你一个无向图(原始图),图中有n个节点,编号从0到n-1。你决定将图中的每条边细分为一条节点链,每条边之间的新节点数各不相同。图用由边组成的二维数组edges表示,其......
  • [边数限制最短路 倍增floyd 矩阵优化]Cow Relays G
    [边数限制最短路倍增floyd矩阵优化]CowRelaysG题目思路边数限制的最短路?bellman_ford可以拿来解决边数<=k的最短路,但这题是边数恰好为k,可以通过奇妙操作改成恰好经过k......
  • Dijkstra算法求带权图的单源最短路径
    Dijkstra算法:给出一个带权无向图,要求指定顶点到图中每一个点的最短路径。首先我们定义一个邻接矩阵c,c[i][j]用来表示从顶点i到顶点j的权重,用一个一维数组prev[]来记录指定......