2 条题解
-
1
#include<bits/stdc++.h> using namespace std; #define int long long const int N=5e5+10; #define PII pair<int,int> #define fi first #define se second vector<PII>G[N]; int d[N],v[N],st,ed,pre[N],n; void dij() { for(int i=1;i<=n;i++)d[i]=1e18; priority_queue<PII,vector<PII>,greater<PII>>q; d[st]=0;q.push({0,st}); while(!q.empty()) { int x=q.top().se;q.pop(); if(v[x])continue;v[x]=1; for(auto i:G[x]) { int y=i.fi,w=i.se; if(d[y]>d[x]+w) { d[y]=d[x]+w; pre[y]=x; if(!v[y])q.push({d[y],y}); } } } } signed main() { int m;cin>>n>>m>>st>>ed;st++,ed++; for(int i=1;i<=m;i++) { int x,y,w;cin>>x>>y>>w;x++,y++; G[x].push_back({y,w}); } dij(); if(d[ed]!=1e18) { stack<PII>stk; int z=ed; while(z!=st) { stk.push({pre[z],z}); z=pre[z]; } cout<<d[ed]<<' '<<stk.size()<<'\n'; while(!stk.empty())cout<<stk.top().fi-1<<' '<<stk.top().se-1<<'\n',stk.pop(); return 0; } cout<<-1<<'\n'; return 0; } -
0
我来水题解了!!!
kevin的代码,我写了点注释,dij详见P1088
#include<bits/stdc++.h> using namespace std; #define int long long const int N=5e5+10; #define PII pair<int,int> #define fi first #define se second vector<PII>G[N]; int d[N],v[N],st,ed,pre[N],n; void dij()//标准的 Dijkstra { for(int i=1;i<=n;i++)d[i]=1e18; priority_queue<PII,vector<PII>,greater<PII>>q; d[st]=0;q.push({0,st}); while(!q.empty()) { int x=q.top().se;q.pop(); if(v[x])continue;v[x]=1; for(auto i:G[x]) { int y=i.fi,w=i.se; if(d[y]>d[x]+w) { d[y]=d[x]+w; pre[y]=x;//当y找到了到它的最短路,记录它的前缀(父亲节点) if(!v[y])q.push({d[y],y}); } } } } signed main() { int m;cin>>n>>m>>st>>ed;st++,ed++;//题目要求0~n-1,不习惯 for(int i=1;i<=m;i++) { int x,y,w;cin>>x>>y>>w;x++,y++; G[x].push_back({y,w}); } dij(); if(d[ed]!=1e18)//如果有路(简单图不保证联通) { stack<PII>stk;//记录答案 int z=ed; while(z!=st)//从结束点开始不停访问前缀 { stk.push({pre[z],z}); z=pre[z]; } cout<<d[ed]<<' '<<stk.size()<<'\n'; while(!stk.empty())cout<<stk.top().fi-1<<' '<<stk.top().se-1<<'\n',stk.pop(); return 0; } cout<<-1<<'\n'; return 0;//完结撒花 }
- 1
信息
- ID
- 8161
- 时间
- 500ms
- 内存
- 1024MiB
- 难度
- 7
- 标签
- 递交数
- 53
- 已通过
- 12
- 上传者