1111 Online Map(迪杰斯特拉+DFS)

Posted keep23456

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了1111 Online Map(迪杰斯特拉+DFS)相关的知识,希望对你有一定的参考价值。

题目:https://pintia.cn/problem-sets/994805342720868352/problems/994805358663417856

输出要求:

技术图片

 翻译结果:

在最短路径不唯一的情况下,输出最短路径中最快的一条,保证唯一。

如果最快的路径不是唯一的,则输出通过最少交叉口的路径,该交叉口保证是唯一的。
如果最短路径和最快路径相同,请按以下格式将它们打印在一行中:

题目思路很简答,使用两个不同度量(距离、时间)的 迪杰斯特拉+DFS 求解即可

PS:我英语好菜,我翻译错了,导致做不出来,呜呜呜~~

  1 #include<iostream>
  2 #include<vector>
  3 #include<algorithm>
  4 using namespace std;
  5 const int maxn = 510;
  6 const int inf = 0x3fffffff;
  7 int G[maxn][maxn],Time[maxn][maxn],n,m,v1,v2,flag,length,TIME,st,ed;
  8 bool visited[maxn];
  9 
 10 int d[maxn],t[maxn];
 11 vector<int> pre[maxn];
 12 vector<int> path1,path2,tempPath;
 13 
 14 void dijkstra1(int st) {
 15     fill(visited,visited+maxn,false);
 16     fill(d,d+maxn,inf);
 17     d[st] = 0;
 18     for(int i = 0; i < n; ++i) {
 19         int u = -1,MIN = inf;
 20         for(int j = 0; j < n; ++j) {
 21             if(!visited[j] && d[j] < MIN) {
 22                 u = j;
 23                 MIN = d[j];
 24             }
 25         }
 26         if(u == -1) return ;
 27         visited[u] = true;
 28         for(int v = 0; v < n; ++v) {
 29             if(!visited[v] && G[u][v] != inf) {
 30                 if(d[u]+G[u][v] < d[v]) {
 31                     d[v] = d[u]+G[u][v];
 32                     pre[v].clear();
 33                     pre[v].push_back(u);
 34                 } else if(d[u]+G[u][v] == d[v])
 35                     pre[v].push_back(u);
 36             }
 37         }
 38     }
 39 }
 40 
 41 void dijkstra2(int st) {
 42     fill(visited,visited+maxn,false);
 43     fill(d,d+maxn,inf);
 44     d[st] = 0;
 45     for(int i = 0; i < n; ++i) {
 46         int u = -1,MIN = inf;
 47         for(int j = 0; j < n; ++j) {
 48             if(!visited[j] && d[j] < MIN) {
 49                 u = j;
 50                 MIN = d[j];
 51             }
 52         }
 53         if(u == -1) return ;
 54         visited[u] = true;
 55         for(int v = 0; v < n; ++v) {
 56             if(!visited[v] && Time[u][v] != inf) {
 57                 if(d[u]+Time[u][v] < d[v]) {
 58                     d[v] = d[u]+Time[u][v];
 59                     pre[v].clear();
 60                     pre[v].push_back(u);
 61                 } else if(d[u]+Time[u][v] == d[v])
 62                     pre[v].push_back(u);
 63             }
 64         }
 65     }
 66 }
 67 int minLength, minTime;
 68 void DFS1(int v) {
 69     if(v == st) {
 70         tempPath.push_back(v);
 71         int sumLength = 0,sumTime = 0;
 72         for(int i = tempPath.size()-1; i > 0; --i) {
 73             v1 = tempPath[i],v2 = tempPath[i-1];
 74             sumLength += G[v1][v2];
 75             sumTime += Time[v1][v2];
 76         }
 77         if(sumLength < minLength) {
 78             minLength = sumLength;
 79             minTime = sumTime;
 80             path1 = tempPath;
 81         } else if(sumLength == minLength && sumTime < minTime) {
 82             minTime = sumTime;
 83             path1 = tempPath;
 84         }
 85         tempPath.pop_back();
 86         return ;
 87     }
 88     tempPath.push_back(v);
 89     for(int i = 0; i < pre[v].size(); ++i)
 90         DFS1(pre[v][i]);
 91     tempPath.pop_back();
 92 }
 93 
 94 void DFS2(int v) {
 95     if(v == st) {
 96         tempPath.push_back(v);
 97         int sumTime = 0;
 98         for(int i = tempPath.size()-1; i > 0; --i) {
 99             v1 = tempPath[i],v2 = tempPath[i-1];
100             sumTime += Time[v1][v2];
101         }
102         if(sumTime < minTime) {
103             minTime = sumTime;
104             path2 = tempPath;
105         } else if(sumTime == minTime && tempPath.size() < path2.size())
106             path2 = tempPath;
107         tempPath.pop_back();
108         return ;
109     }
110     tempPath.push_back(v);
111     for(int i = 0; i < pre[v].size(); ++i)
112         DFS2(pre[v][i]);
113     tempPath.pop_back();
114 }
115 int main() {
116     fill(G[0],G[0]+maxn*maxn,inf);
117     fill(Time[0],Time[0]+maxn*maxn,inf);
118     cin>>n>>m;
119     for(int i = 0; i < m; ++i) {
120         cin>>v1>>v2>>flag>>length>>TIME;
121         G[v1][v2] = length,Time[v1][v2] = TIME;
122         if(flag == 0)  G[v2][v1] = G[v1][v2],Time[v2][v1] = Time[v1][v2];
123     }
124     cin>>st>>ed;
125     dijkstra1(st);
126     minLength = inf, minTime = inf;
127     DFS1(ed);
128     tempPath.clear();
129     minTime = inf;
130     dijkstra2(st);
131     DFS2(ed);
132     if(path1 == path2) printf("Distance = %d; ",minLength);
133     else {
134         printf("Distance = %d: ",minLength);
135         for(int i = path1.size()-1; i >= 0; --i) {
136             if(i < path1.size()-1) printf(" -> ");
137             printf("%d",path1[i]);
138         }
139         printf("
");
140     }
141     printf("Time = %d: ",minTime);
142     for(int i = path2.size()-1; i >= 0; --i) {
143         if(i < path2.size()-1) printf(" -> ");
144         printf("%d",path2[i]);
145     }
146     return 0;
147 }

技术图片

 

以上是关于1111 Online Map(迪杰斯特拉+DFS)的主要内容,如果未能解决你的问题,请参考以下文章

迪杰斯特拉(Dijkstra)算法

pat1003 迪杰斯特拉法和dfs求最短路

LeetCode 743 网络延迟时间[最短路径 迪杰斯特拉 Floyd] HERODING的LeetCode之路

求多重邻接表的迪杰斯特拉算法

迪杰斯特拉算法为啥不能有负权边

迪杰斯特拉算法的算法思想