最短路算法的SPFA算法
来源:互联网 发布:高中地理优化设计 编辑:程序博客网 时间:2024/05/22 17:02
看见很多人写的博客,有很多很详细的过程还有具体的图的解释,但是好像没看见什么博客把自己的思路写出来的代码做一个详细的解释(我也是听很多师哥的讲解,然后写的代码),所以就在这里把代码做一个更详细的解释。
特点:
可以处理负边,只要最短路径存在,就一定可以求出最小值
判断有无负环:如果某点进入队列的次数超过N次,则存在负环(该算法无法处理带负环的图)
负回路:该图所有权值得和小于零,则形成了负回路。
模板代码:
#include<cstdio>
#include<iostream>
#include<queue>
#include<cstring>
using namespace std;
#define N 1000000
const int inf=0x3f3f3f3f;
int nodeNum,edgeNum;//结点的数量和边的数量;
int d[N];//数组d[i]表示源点s到i的距离
int c[N];//统计每一个结点入队的次数
bool vis[N];
bool loop;//判断是否有回路
map[nodeNum][nodeNum];//存之间的点
void spfa(int start)//先传入开始的点
{
queue<int>q;//建立队列,初始化几个数组
memset(vis,false,sizeof(vis))//false代表还没有入队
for(int i=1;i<=nodeNum;i++)
dis[i]=inf;//先把之间的距离初始化为最大值
dis[start]=true;//源点初始化为真
q.push(start);//源点入队
vis[start]=1;//源点标记为1
}
while(!q.empty())//判断队列是否为空,如果为空,则说明已经遍历完毕
{//入队时要用vis数组标记一下
int temp=q.front();
q.pop();//取走队头的元素
vis[q]=flase;//取走后再出队,消除标记
for(int i=1;i<=nodeNum;i++)
{
if(dis[temp]+map[temp][i]<dis[i])//和之前算法一样的松弛操作
{
dis[i]=dis[temp]+map[temp][i];
if(!vis[i])//判断相邻的结点是否在队列中
{
q.push(i);
vis[i]=true;
}
}
}
}
但是这个算法不是很稳定,期望的时间复杂度O(ke),其中k为所有顶点进队的平均次数,k一般小于等于2;
算法的优化方法:
1),SLF优化:
当你要向队列中添加结点的时候,现将其与队首元素进行比较,如果比当前已知的最短距离更小一些,那么将其放在队首的位置,否则放到队尾。
2),LLL优化
设队首元素为i,队列中所有dis的平均值为x,若dis>x,则将i插入到队尾,查找下一个元素,知道dia<=i,,则出队进行松弛操作。
- 最短路算法的SPFA算法
- 最短路--SPFA算法
- 最短路SPFA算法
- 最短路: SPFA算法
- spfa算法 最短路
- SPFA最短路算法
- hdu2544 最短路(SPFA算法)
- 最短路算法(SPFA)
- SPFA算法之最短路。
- 关于最短路算法SPFA
- 最短路(SPFA)算法
- 最短路SPFA 算法详解
- SPFA算法 (最短路)
- 最短路【SPFA】算法模板
- SPFA最短路算法解析
- 最短路之SPFA算法
- 最短路SPFA算法模板
- 浅谈最短路-SPFA算法
- 面试笔记。
- win10_64安装Cplex12.5
- 多线程_继承Thread类的方式卖电影票案例
- linux常用命令(7、8)-网络命令、关机重启命令
- linux的pidof命令
- 最短路算法的SPFA算法
- 算法总结1
- 《Effective C++》关于const,define等总结
- 002使用两个栈模拟队列的基本操作
- 【面试题8】旋转数组的最小数字
- 运行android studio 在模拟器上找不到自己做的app
- 1.5 点
- 阿福工作感悟之卖掉你的想法
- MongoDB集群配置(一)