HDU 1385(Minimum Transport Cost)floyd+正向返回路径

来源:互联网 发布:新浪云平台数据库 编辑:程序博客网 时间:2024/05/21 19:40

题意:给你n个城市,和两两城市之间运送货物的花费,以及每个城市的关税(note:关税只有在通过这个城市的时候才可以缴纳),还有一个要注意的地方就是最短路径不是任意的,要求输出符合字典序的,eg:起点到终点的最小权同为min的有两条路径,1-->3和1-->2-->3那么我们输出的时候就应该是先比较第一个数,如果一样那么比较第二个数,一直到出现第一个不一样的数为止,然后输出数较小的那条路径,如果一条路径比完了,而另一条路径还有点,那么就输出经过点较短的那个(看清前面的前提条件)。发火此题还有一个大坑点:发火就是起点和终点一样时,输出start-->start就会wa,应该是输出start。还有一个就是记录路径的问题,由于要从前则有录取者用path数组是记录一个点的后继点(这里标注是因为我的习惯是记录前继点)。

path[a][b]:终点为b,点a的下一个点。初始化的时候path[a][b]=b

#include<iostream>#include<cstring>#include<cstdio>#define inf 0x7ffffffusing namespace std;const int N=500+5;int map[N][N],tax[N];int path[N][N];//path[a][b]:终点为b点a的下一个点。 int n;int Min(int a,int b){if(a<b) return a;return b;}void floyd(){for(int k=1;k<=n;k++){for(int i=1;i<=n;i++){for(int j=1;j<=n;j++){if(map[i][j]>map[i][k]+map[k][j]+tax[k]){map[i][j]=map[i][k]+map[k][j]+tax[k];path[i][j]=path[i][k];}else if(map[i][j]==map[i][k]+map[k][j]+tax[k])//选择的前提条件{path[i][j]=Min(path[i][j],path[i][k]);//这里进行了选择}}}}}void display(int st,int ed)//返回路径的时候要固定它的终点然后再从起点开始找{//int temp=path[st][ed];    //printf("%d",st);//39行和45行保证了当起点和终点相同时也有路径输出int temp=st; //上边那两行就是我被坑的地方,留着while(temp!=ed){printf("%d-->",temp);temp=path[temp][ed];}printf("%d\n",temp);}int main(){while(~scanf("%d",&n),n){for(int i=1;i<=n;i++){for(int j=1;j<=n;j++){path[i][j]=j;scanf("%d",&map[i][j]);if(map[i][j]==-1) map[i][j]=inf;}}for(int i=1;i<=n;i++){scanf("%d",&tax[i]);}floyd();int st,ed;while(1){scanf("%d%d",&st,&ed);if(st==-1&&ed==-1) break;printf("From %d to %d :\n",st,ed);printf("Path: ");display(st,ed);printf("Total cost : %d\n\n",map[st][ed]);}}return 0;} 

0 0
原创粉丝点击