存在一些点构成一张图,经过每个点要收费,求一个点到另一个点的最小花费(收的费和路程)并输出路径(起点与终点不收钱),如果存在多组答案,输出字典序最小的路径;
模板稍改
#include <iostream>
using namespace std;
const int inf=0x3f3f3f3f;
int n;
int pre[1100][1100];
int a[1100][1100];
int cost[1100];
int main()
{
std::ios::sync_with_stdio(false);
cin.tie(0);cout.tie(0);
int u,v,val,e,s,sum,va;
while (cin>>n&&n)
{
for (int i=1;i<=n;i++)
for (int j=1;j<=n;j++)
{
cin>>a[i][j];
if (i==j)
a[i][j]=0;
else if (a[i][j]==-1)
a[i][j]=inf;
pre[i][j]=j;
}
for (int i=1;i<=n;i++)
cin>>cost[i];
for (int k=1;k<=n;k++)
for (int i=1;i<=n;i++)
for (int j=1;j<=n;j++)
{
va=a[i][k]+a[k][j]+cost[k];//可以将价钱换做路程来看
if (a[i][j]>va)
{
a[i][j]=va;
pre[i][j]=pre[i][k];
}
else if (va==a[i][j]) //距离相等求较小字典序
{
if (pre[i][j]>pre[i][k])
pre[i][j]=pre[i][k];
}
}
while (cin>>s>>e)
{
if (s==-1&&e==-1)
break;
int now=pre[s][e];
cout<<"From "<<s<<" to "<<e<<" :"<<endl;
cout<<"Path: "<<s;
if (s==e)
cout<<endl;
else
{
while (1)
{
cout<<"-->"<<now;
if (now==e)
break;
now=pre[now][e];
}
cout<<endl;
}
cout<<"Total cost : "<<a[s][e]<<endl;
cout<<endl;
}
}
return 0;
}