单源最短路径

题目描述

如题,给出一个有向图,请输出从某一点出发到所有点的最短路径长度。

输入输出格式

输入格式:

第一行包含三个整数N、M、S,分别表示点的个数、有向边的个数、出发点的编号。

接下来M行每行包含三个整数Fi、Gi、Wi,分别表示第i条有向边的出发点、目标点和长度。

输出格式:

一行,包含N个用空格分隔的整数,其中第i个整数表示从点S出发到点i的最短路径长度(若S=i则最短路径长度为0,若从点S无法到达点i,则最短路径长度为2147483647)

输入输出样例

输入样例

输出样例

单源最短路(Single-Source Shortest Paths, SSSP)

先上Dijkstra算法

Dikstra 算法适用于边权为正的情况。主要想法是:将一个点走一步能到达的所有结点都放进队列里,并从队列里选择源点到该点路径最短的结点出队。这样就保证出队的结点一定是源点到该点的最短路。那么就能确定放进队列的每一个结点不仅要有该结点的编号,也要有源点到该结点的距离,所以可以用结构体来实现。队列中出队的必须是最小的,那么就可以用优先队列实现。所以开一个结构体优先队列。

 #include<cstdio>
#include<cmath>
#include<iostream>
#include<cstring>
#include<algorithm>
#include<queue>
#include<vector>
using namespace std;
const int maxn = 1e4 + ;
const int INF = ;
struct Grap
{
int num, cost; //num点编号,cost到该点距离
bool operator < (const Grap& other)const
/*优先队列出队的原本是最大的,而我们期望的是最小的,所
以重载小于号,不仅要兼容结构体,还要使逻辑相反 */
{
return cost > other.cost;
}
};
vector<int>v[maxn];
vector<int>c[maxn];
int n, m, k, vis[maxn], dis[maxn];
void dijkstra(int k)
{
for(int i = ; i < maxn; ++i)
dis[i] = INF;
/*初始化设为无穷,同时也代表了源点无法到达的点
的最短路径长度就是无穷*/
memset(vis, , sizeof(vis));
priority_queue<Grap>q;
q.push((Grap){k, });
dis[k] = ;
while(!q.empty())
{
Grap now = q.top(); q.pop();
int node = now.num;
if(vis[node]) continue;
/*如果该点已经出队,那到这个点的路径长度一定是最短路。为了防止
结点的重复扩展,如果发现新取出来的结点曾经被取出来过,应该直接
把它扔掉,所以开一个数组记录。 */
vis[node] = ;
for(int i = ; i < v[node].size(); ++i)
{
if(dis[v[node][i]] > dis[node] + c[node][i])
{
dis[v[node][i]] = dis[node] + c[node][i]; q.push((Grap){v[node][i], dis[v[node][i]]});
}
}
}
}
int main()
{
scanf("%d%d%d", &n, &m, &k);
for(int i = ; i < m; ++i)
{
int a, b, cost; scanf("%d%d%d", &a, &b, &cost);
v[a].push_back(b); c[a].push_back(cost); //用vector建图
}
dijkstra(k);
for(int i = ; i <= n; ++i) printf("%d%s",dis[i], i == n ? "\n" : " ");
return ;
}

再上一个spfa算法

spfa算法不仅可以求最短路,也可以判断一个图中存不存在负圈。在这个算法中,一个结点可能多次入队(出队),最多入队 n 次(结点个数次),而当超过 n 次时,就证明一定存在负圈。

 #include <cstdio>
#include<iostream>
#include<cmath>
#include<queue>
#include<vector>
#include<cstring>
#include<algorithm>
using namespace std;
vector<int>v[], c[];
const int INF = ;
int dis[];
bool vis[];
void spfa(int a)
{
for(int i = ; i < ; ++i) dis[i] = INF;
dis[a] = ;
memset(vis, , sizeof(vis));
queue<int>q;q.push(a);
while(!q.empty())
{
int now = q.front();q.pop();
vis[now] = ; //出队后去除标记
for(int i = ; i < (int)v[now].size(); ++i)
{
if(dis[now] + c[now][i] < dis[v[now][i]])
{
dis[v[now][i]] = dis[now] + c[now][i];
if(!vis[v[now][i]])
{q.push(v[now][i]); vis[v[now][i]] = ;}
}
}
}
}
int main()
{
int n, m, s;
scanf("%d%d%d", &n, &m, &s);
for(int i = ; i < m; ++i)
{
int f, g, w;
scanf("%d%d%d", &f, &g, &w);
v[f].push_back(g);c[f].push_back(w);
}
spfa(s);
for (int i = ; i <= n; i++) printf("%d%c", dis[i], i == n ? '\n' : ' ');
}

图上最短路(Dijkstra, spfa)的更多相关文章

  1. POJ 2387 Til the Cows Come Home(最短路 Dijkstra/spfa)

    传送门 Til the Cows Come Home Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 46727   Acce ...

  2. ACM-最短路(SPFA,Dijkstra,Floyd)之最短路——hdu2544

    ***************************************转载请注明出处:http://blog.csdn.net/lttree************************** ...

  3. 【BZOJ-3627】路径规划 分层图 + Dijkstra + spfa

    3627: [JLOI2014]路径规划 Time Limit: 30 Sec  Memory Limit: 128 MBSubmit: 186  Solved: 70[Submit][Status] ...

  4. [Codeforces 1197E]Culture Code(线段树优化建图+DAG上最短路)

    [Codeforces 1197E]Culture Code(线段树优化建图+DAG上最短路) 题面 有n个空心物品,每个物品有外部体积\(out_i\)和内部体积\(in_i\),如果\(in_i& ...

  5. dijkstra spfa prim kruskal 总结

    最短路和最小生成树应该是很早学的,大家一般都打得烂熟,总结一下几个问题 一  dijkstra  O((V+E)lgV) //V节点数 E边数 dijkstra不能用来求最长路,因为此时局部最优解已经 ...

  6. POJ3662 [USACO08JAN]Telephone Lines (二分答案/分层图求最短路)

    这道题目有两种解法: 1.将每个点视为一个二元组(x,p),表示从起点到x有p条路径免费,相当于构建了一张分层图,N*k个节点,P*k条边.在这张图上用优先队列优化的SPFA算法求解,注意这里的d数组 ...

  7. 算法学习笔记(三) 最短路 Dijkstra 和 Floyd 算法

    图论中一个经典问题就是求最短路.最为基础和最为经典的算法莫过于 Dijkstra 和 Floyd 算法,一个是贪心算法,一个是动态规划.这也是算法中的两大经典代表.用一个简单图在纸上一步一步演算,也是 ...

  8. 最短路Dijkstra算法的一些扩展问题

    最短路Dijkstra算法的一些扩展问题     很早以前写过关于A*求k短路的文章,那时候还不明白为什么还可以把所有点重复的放入堆中,只知道那样求出来的就是对的.知其然不知其所以然是件容易引发伤痛的 ...

  9. Til the Cows Come Home 最短路Dijkstra+bellman(普通+优化)

    Til the Cows Come Home 最短路Dijkstra+bellman(普通+优化) 贝西在田里,想在农夫约翰叫醒她早上挤奶之前回到谷仓尽可能多地睡一觉.贝西需要她的美梦,所以她想尽快回 ...

随机推荐

  1. JavaScript事件(含Demo)

    主要事件: onclick 鼠标单击事件 onmouseover 鼠标经过事件 onmouseout 鼠标移开事件 onchange 文本框内容改变事件 onselect 文本框内容被选中事件 onf ...

  2. CSS基础知识思维导图xmind

    这是我根据自己的学习笔记整理的思维导图,WEB前端的知识很多,汇总来看会比较清晰.

  3. 04-HTML-图片标签

    <html> <head>  <title>图片标签学习</title>  <meta charset="utf-8"/> ...

  4. jQuery: 选择器,筛选器

    jQuery 简介 jQuery由美国人John Resig创建,至今已吸引了来自世界各地的众多 javascript高手加入其team. jQuery是继prototype之后又一个优秀的Javas ...

  5. jquery 树形导航菜单无限级

    转自:http://www.jb51.net/article/71615.htm 侵删<!DOCTYPE html> <html lang="en"> &l ...

  6. tomcat闪退解决

    异常原因:拷贝了一个tomcat到新机器上,运行startup闪退 解决方法: 1.检查发现当前系统没有安装配置jdk,安装配置后运行仍然闪退 2.在tomcat的启动脚本和关闭脚本中指定JDK和to ...

  7. MMU学习总结

    待完善 一.MMU主要完成哪些事务? 二.PowerPC上的BAT.LAW是做什么用的? 三.

  8. Implemented the “Importance Sampling of Reflections from Hair Fibers”

      Just the indirect specular pass by importance sampling. With all layers. Manually traced by 3D Ham ...

  9. OkHttpUtils简单的网络去解析使用

    先添加依赖: implementation 'com.google.code.gson:gson:2.2.4' implementation 'com.zhy:okhttputils:2.0.0' 网 ...

  10. 快速开发跨平台应用之Xamarin技术

    Xamarin 介绍 Xamarin 是一个允许开发人员有效创建可跨 iOS.Android.Windows 应用程序的开发工具集.Xamarin是免费且开源的,遵循 MIT (麻省理工学院许可证)协 ...