迪杰斯特拉--记录路径
Posted accepting
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了迪杰斯特拉--记录路径相关的知识,希望对你有一定的参考价值。
迪杰斯特拉记录路径的办法就是开一个数组, 记录一下该节点的上一个节点是谁最后在递归输出就可以了
例题:
B. wzy的大冒险——出发咯QAQ
单点时限: 2.0 sec
内存限制: 512 MB
wzy踏上了冒险的旅程。
现在他从地精手里买了一份地图,地图上有n个城镇。
他从第一个城镇出发,走向(没钱只能走)第n个城镇,现在,请你帮wzy找到一条最短的路径,并倒序(从n到1)输出一条最短路径。
举个栗子:如果有两条路径6 4 3 1和6 5 2 1,我们选择6 4 3 1这条。
地精小提示:路是单向的QAQ。
输入格式
第一行两个数n,m ,(1≤n≤103,1≤m≤103)
接下来m行,每行三个数x,y,z,表示点 x 与点 y 之间有一条权值为 z 的有向边 (1≤x,y,z≤103).
输出格式
第一行一个整数表示 1 到 n 的最短距离;
第二行倒序输出这条路径。
样例
input
5 7 1 2 69 1 3 87 1 4 79 2 5 94 2 3 10 3 5 79 4 5 43
output
122 5 4 1
#include<iostream> #include<cstring> #include<cstdio> using namespace std; const int N=1E4+7; const int INF=0x3f3f3f3f; int map[N][N]; int dis[N]; int pre[N]; int mark[N]; int n,m; void djstrea(int x) memset(mark,0,sizeof(mark)); for(int i=1;i<=n;i++) dis[i]=map[x][i]; dis[x]=0; mark[x]=1; for(int i=1;i<=n;i++) int ans=INF; int pos; for(int i=1;i<=n;i++) if(mark[i]==0&&ans>dis[i]) ans=dis[i]; pos=i; mark[pos]=1; for(int i=1;i<=n;i++) if(dis[i]>ans+map[pos][i]) dis[i]=ans+map[pos][i]; pre[i]=pos;//先到pos再到i,因此i是pos的父节点 int main() cin>>n>>m; int x,y,z; for(int i=0;i<=n;i++) pre[i]=-1; memset(map,INF,sizeof(map)); for(int i=1;i<=m;i++) scanf("%d%d%d",&x,&y,&z); map[x][y]=z;//本题目是单向的 djstrea(1); cout<<dis[n]<<endl; for(int i=n;i!=-1;i=pre[i]) cout<<i<<" "; cout<<1<<endl;//起点 return 0;
地杰斯特拉(堆优化+路径记录)
还是这个题目:题目中的队列保持的是点x,与点x到起点的距离,然后优先队列,没词都取出来较小的一个
#include<iostream> #include<cstdio> #include<vector> #include<queue> #include<cstring> using namespace std; const int N=1E5+7; const int INF=0x3f3f3f3f; typedef long long ll; struct stu ll a,b; ; int pre[N]; ll dis[N]; int mark[N]; vector<stu>ve[N]; struct node int x,y; bool friend operator<(const node x1,const node y1) return x1.y>y1.y; ; void djstrea(int s) memset(mark,0,sizeof(mark)); memset(dis,INF,sizeof(dis)); priority_queue<node>que; dis[s]=0; que.push(s,0); while(que.size()) node xx=que.top(); que.pop(); if(mark[xx.x]==1) continue ; mark[xx.x]=1; for(int i=0;i<ve[xx.x].size();i++) int dx=ve[xx.x][i].a; int dy=ve[xx.x][i].b; if(mark[dx]==0&&dis[dx]>dis[xx.x]+dy) dis[dx]=dis[xx.x]+dy; if(mark[dx]==0) que.push(dx,dis[dx]); pre[dx]=xx.x; int main() int n,m,s; cin>>n>>m; s=1; for(int i=0;i<=n;i++) pre[i]=-1; int x,y,z; for(int i=1;i<=m;i++) scanf("%d%d%d",&x,&y,&z); ve[x].push_back(y,z); djstrea(s); cout<<dis[n]<<endl; for(int i=n;i!=-1;i=pre[i]) cout<<i<<" "; return 0;
以上是关于迪杰斯特拉--记录路径的主要内容,如果未能解决你的问题,请参考以下文章