zoj 3396

来源:互联网 发布:发表小说的软件 编辑:程序博客网 时间:2024/06/06 19:23
今天又放弃了一个项目的机会。。
有时候觉得自己的选择到底是不是对的。。为ACM放弃了许多。。真的可以得到我想要的吗。。
不管怎样,我已经没有退路了,牺牲了很多,无论如何都要奋斗到底!!

记得对部长的承诺,记得奶奶重病是对我说的许多,记得bu一直的支持,记得XJ跟我说的,xsbailong,fighting~


/*zoj_3396    最短路dijkstra过的。相对简单的一道题。但是有个陷阱很阴人。。题意:有m个转换器,求使给出的三个转换器连通的最短路径。Process:1.一开始看的m才500的数据,直接对每个节点来个dijk。。果断TLE了。2.后来发现q限定了50而已,毫无疑问改成了对给定数据x,y,z的dijk。3.然后是wa。。找了N久错。。实在晕了又是求助百度,立马找到了原因,  感觉这是本题最大的陷阱:  x.y.z三个转换器的中间点可能是m个转换器的任何一个!!!  而我一开始一直被sample误导,认为必定是x、y、z中的一个。。所以思路变成了这样:对x、y、z都进行一次dijk,枚举中间点(1-m)找到最小。*/#include <iostream>#include <cstdio>#include <string.h>#include <limits.h>#define N 10010using namespace std;int tran[N];int map[510][510];int dist[510][510];int flag[510];bool mark[510];void inint(){    int i,j;    memset( mark,0,sizeof(mark) );    for( i=0;i<510;i++ )        for( j=0;j<510;j++ )        {            if( i==j )  map[i][j]=0 , dist[i][j]=0 ;            else map[i][j]=-1 , dist[i][j]=-1 ;        }}void dijkstra( int from,int n ){    int i,j,mark,mini,sta;    memset( flag,0,sizeof(flag) );    sta=from;    flag[sta]=1;    for( i=0;i<n;i++ )    {        mini=INT_MAX;        for( j=1;j<=n;j++ )        {            if( !flag[j] )            {                if( map[sta][j]!=-1 && dist[from][j]>dist[from][sta]+map[sta][j] )                    dist[from][j]=dist[from][sta]+map[sta][j];                else if( map[sta][j]!=-1 && dist[from][j]==-1 )                    dist[from][j]=dist[from][sta]+map[sta][j];                if( mini>dist[from][j] && dist[from][j]!=-1 )                {                    mini=dist[from][j];                    mark=j;                }            }        }        if( mini==INT_MAX ) break;        sta=mark;        flag[sta]=1;    }}bool check( int a,int b,int c ){    if( dist[a][b]==-1 || dist[a][c]==-1 )        return false;    return true;}int main(){    //freopen( "AAA_a.txt","r",stdin );    int n,m,l,i;    int a,b,c,v;    int count1,count2;    count1=1;    while( scanf("%d%d%d",&n,&m,&l)!=EOF )    {        inint();        for( i=1;i<=n;i++ )            scanf( "%d",&tran[i] );        for( i=0;i<l;i++ )        {            scanf( "%d%d%d",&a,&b,&v );            map[a][b]=v;            map[b][a]=v;        }        scanf( "%d",&n );        printf( "Case #%d\n",count1 );        count2=1;        while( n-- )        {            scanf( "%d%d%d",&a,&b,&c );            a=tran[a] , b=tran[b] , c=tran[c];            if( mark[a]==0 )    mark[a]=1 , dijkstra( a,m );            if( mark[b]==0 )    mark[b]=1 , dijkstra( b,m );            if( mark[c]==0 )    mark[c]=1 , dijkstra( c,m );            if( check( a,b,c ) )            {                v=INT_MAX;                for( i=1;i<=m;i++ )                    if( v>dist[a][i]+dist[b][i]+dist[c][i] )                        v=dist[a][i]+dist[b][i]+dist[c][i];                printf( "Line %d: The minimum cost for this line is %d.\n",count2,v );            }            else printf( "Line %d: Impossible to connect!\n",count2 );            count2++;        }        count1++;    }    return 0;}