hdu 3790 最短路径问题

来源:互联网 发布:注塑机械手调试与编程 编辑:程序博客网 时间:2024/05/21 04:16
Problem Description
给你n个点,m条无向边,每条边都有长度d和花费p,给你起点s终点t,要求输出起点到终点的最短距离及其花费,如果最短距离有多条路线,则输出花费最少的。
 
Input
输入n,m,点的编号是1~n,然后是m行,每行4个数 a,b,d,p,表示a和b之间有一条边,且其长度为d,花费为p。最后一行是两个数 s,t;起点s,终点。n和m为0时输入结束。
(1<n<=1000, 0<m<100000, s != t)
 
Output
输出 一行有两个数, 最短距离及其花费。
 
Sample Input
3 21 2 5 62 3 4 51 30 0
 
Sample Output
9 11
#include<stdio.h>#include<string.h>#define N 1005#define max 99999999struct node{    int d,p;}map[N][N],f[N];int n,m,mark[N],s,t;void in(){     int i,j;     for(i=1;i<=n;i++)     {          for(j=1;j<=n;j++)          {           map[i][j].d=max;           map[i][j].p=max;          }     }}void di(){     int i,j,k,min,min1;     memset(mark,0,sizeof(mark));     for(i=1;i<=n;i++)     {      f[i].d=map[s][i].d;      f[i].p=map[s][i].p;     }     //mark[s]=1;     f[s].d=f[s].p=0;//如果用这种方式则i可以等于n,否则换成上面一句去"="     for(i=1;i<=n;i++)     {          min=max;min1=max;          for(j=1;j<=n;j++)          {           if(!mark[j]&&(f[j].d<min||f[j].d==min&&f[j].p<min1))//进行对比,两个条件,距离小的或距离一样花费小的。           {            min=f[j].d;            min1=f[j].p;            k=j;           }          }          if(min==max)break;          mark[k]=1;          for(j=1;j<=n;j++)          {               if(!mark[j]&&((f[j].d>f[k].d+map[k][j].d)||(f[j].d==f[k].d+map[k][j].d&&f[j].p>f[k].p+map[k][j].p)))               {                f[j].d=f[k].d+map[k][j].d;                f[j].p=f[k].p+map[k][j].p;               }          }     }}int main(){     int i,a,b,d,p;     while(scanf("%d%d",&n,&m),n||m)     {          in();          for(i=0;i<m;i++)          {               scanf("%d%d%d%d",&a,&b,&d,&p);               if(map[a][b].d>d||(map[a][b].d==d&&map[a][b].p>p))               {                map[a][b].d=map[b][a].d=d;                map[a][b].p=map[b][a].p=p;               }          }          scanf("%d%d",&s,&t);          di();          printf("%d %d\n",f[t].d,f[t].p);     }     return 0;}


0 0
原创粉丝点击