\quad 这是一道最短路题,代码量挺大的,需要记录路劲,两个求解的子问题
- 求最短距离以及在最短距离一样的情况下所需要的最少时间
- 求最少花费时间,以及时间一样的情况下经过的路的条数最少
\quad 我用spfa求解最短路,用from数组记录路劲。程序挺多的,是个手速题,如下:
#include <iostream>
#include <vector>
#include <queue>
#include <bits/stdc++.h>
using namespace std;
const int maxn = 501;
vector<pair<int, int> > Length[maxn], Time[maxn];
int s, t;
int len[maxn], timecost[maxn];
int from[maxn], vis[maxn], inq[maxn];
int res1, res2;
int nodeNum[maxn];
stack<int> spfa_Len()
{
for (int i = 0; i < maxn; ++i)
{
len[i] = 0x3f3f3f3f;
timecost[i] = 0x3f3f3f3f;
}
len[s] = 0;
timecost[s] = 0;
queue<int> q;
q.push(s);
inq[s] = 1;
while(!q.empty())
{
int now = q.front();
q.pop();
inq[now] = 0;
for (int i = 0; i < Length[now].size(); ++i)
{
int next = Length[now][i].first;
int w = Length[now][i].second;
int ct = Time[now][i].second;
if(len[now]+w<len[next])
{
len[next] = len[now]+w;
timecost[next] = timecost[now]+ct;
from[next] = now;
if(inq[next]==0)
{
q.push(next);
inq[next] = 1;
}
}
else if(len[now]+w==len[next] && timecost[now]+ct<timecost[next])
{
timecost[next] = timecost[now]+ct;
from[next] = now;
if(inq[next]==0)
{
q.push(next);
inq[next] = 1;
}
}
}
}
res1 = len[t];
stack<int> st;
st.push(t);
int temp = from[t];
while(temp!=s)
{
st.push(temp);
temp = from[temp];
}
st.push(s);
return st;
}
stack<int> spfa_time()
{
for (int i = 0; i < maxn; ++i)
{
timecost[i] = 0x3f3f3f3f;
from[i] = 0;
nodeNum[i] = 0;
}
timecost[s] = 0;
queue<int> q;
q.push(s);
vis[s] = 1;
while(!q.empty())
{
int now = q.front();
q.pop();
vis[now] = 0;
for (int i = 0; i < Time[now].size(); ++i)
{
int next = Time[now][i].first;
int w = Time[now][i].second;
if(timecost[now]+w<timecost[next])
{
timecost[next] = timecost[now]+w;
nodeNum[next] = nodeNum[now]+1;
from[next] = now;
if(vis[next]==0)
{
q.push(next);
vis[next] = 1;
}
}
else if(timecost[now]+w==timecost[next] && nodeNum[now]+1<nodeNum[next])
{
from[next] = now;
nodeNum[next] = nodeNum[now]+1;
if(vis[next]==0)
{
q.push(next);
vis[next] = 1;
}
}
}
}
res2 = timecost[t];
stack<int> st;
st.push(t);
int temp = from[t];
while(temp!=s)
{
st.push(temp);
temp = from[temp];
}
st.push(s);
return st;
}
void show_len(stack<int> st)
{
cout << "Distance = " << res1 << ": ";
while(!st.empty())
{
cout << st.top();
if(st.top()!=t) cout << " -> ";
st.pop();
}
cout << endl;
}
void show_time(stack<int> st)
{
cout << "Time = " << res2 << ": ";
while(!st.empty())
{
cout << st.top();
if(st.top()!=t) cout << " -> ";
st.pop();
}
cout << endl;
}
int main(int argc, char const *argv[])
{
ios::sync_with_stdio(false);
int n, m;
cin >> n >> m;
for (int i = 0; i < m; ++i)
{
int a, b, c, d, e;
cin >> a >> b >> c >> d >> e;
Length[a].push_back(make_pair(b, d));
Time[a].push_back(make_pair(b, e));
if(c==0)
{
Length[b].push_back(make_pair(a, d));
Time[b].push_back(make_pair(a, e));
}
}
cin >> s >> t;
stack<int> s1 = spfa_Len();
stack<int> s2 = spfa_time();
if(s1!=s2)
{
show_len(s1);
show_time(s2);
}
else
{
cout << "Distance = " << res1 << "; ";
show_time(s2);
}
return 0;
}