CSU1333最短路问题SPFA
Posted df-yimeng
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了CSU1333最短路问题SPFA相关的知识,希望对你有一定的参考价值。
fastvj.rainng.com/contest/236779#problem/I
Description:
n个点m条路每条路 l,r,t:表示这条路开l秒,关r秒,通过要t秒,问你车辆从s到t最少要多少秒
Solution:
(刷着最大流突然看到了我亲爱的最短路,真的是我相见恨晚,而且还是这个专题的最后一题,嘿嘿嘿,拿下)
考点就是spfa的松弛操作,dis表示当前到now点的时间,你要判断现在t秒能不能通过下一条路,可以的话松弛就是dis[now] + t,不行的话你得等,等到那个路通了再走,dis[now] + wait + t;
还是比较年轻,存在有的路开通时间小于通过时间,那些边不予考虑!
Code:
#include <iostream> #include <queue> #include <cstdio> #include <cstring> #include <algorithm> #define inf (1 << 28) using namespace std; const int maxn = 5e4 + 5; const int maxm = 5e4 + 5e3; struct node{ int to,l,r,t,pre; }e[maxm]; int id[maxn],cnt; //spfa int dis[maxn]; int vis[maxn]; void init() { memset(vis,0,sizeof(vis)); memset(id,-1,sizeof(id)); cnt = 0; } void add(int from,int to,int l,int r,int t) { e[cnt].to = to; e[cnt].l = l; e[cnt].r = r; e[cnt].t = t; e[cnt].pre = id[from]; id[from] = cnt++; } void spfa(int s,int n) { for(int i = 0;i <= n;++i) dis[i] = inf; dis[s] = 0; vis[s] = 1; queue<int> q; q.push(s); while(q.size()) { int now = q.front(); q.pop(); for(int i = id[now];~i;i = e[i].pre) { int to = e[i].to; int t = e[i].t; int l = e[i].l; int r = e[i].r; int tot = l + r; int cost; if((dis[now] % tot) + t <= l)cost = t; else cost = r + (l - (dis[now] % tot)) + t; if(dis[to] > dis[now] + cost) { dis[to] = dis[now] + cost; if(!vis[to]) { vis[to] = 1; q.push(to); } } } vis[now] = 0; } return; } int main() { int S,T,n,m; int cas = 1; while(~scanf("%d%d%d%d",&n,&m,&S,&T)) { init(); int from,to,l,r,t; for(int i = 1;i <= m;++i) { scanf("%d%d%d%d%d",&from,&to,&l,&r,&t); //没考虑到啊!!!! if(l>=t) add(from,to,l,r,t); } spfa(S,n); printf("Case %d: %d ",cas++,dis[T]); } return 0; }
以上是关于CSU1333最短路问题SPFA的主要内容,如果未能解决你的问题,请参考以下文章
CSU 2005 Nearest Maintenance Point(最短路+bitset)