当前位置: 代码迷 >> 综合 >> POJ 3613 图论思想转化
  详细解决方案

POJ 3613 图论思想转化

热度:38   发布时间:2024-01-20 20:52:00.0

很有意思的题= =..... 紧跟zzy大神的步伐A题.... 这里结合离散数学的知识:

离散数学中图的矩阵表示法 用i,j为1表示i到j有一条边,A*A即A^2就是说i-j为2条边的路径种类有多少条。但是这个题的话是运用Floyd的思想,每次更新边使得路径条数+1.多的不说了 不说i我的思想。但是对图论的理解又进了一步!

#include<iostream>
#define MAXEdge 1000005
#define MAXN 1005
using namespace std;int dist[MAXN][MAXN];
struct Edge
{int u,v,price;
}edge[MAXEdge];struct Floyd
{int ans[101][101];
};int N,T,S,E;
int cnt;
Floyd YB;void Matrix2( Floyd &a,Floyd b )
{Floyd K;memset( K.ans,0x6F,sizeof(K.ans) ); int i,j,k;for( k=1;k<=cnt;k++ )for( i=1;i<=cnt;i++ )for( j=1;j<=cnt;j++ )if( K.ans[i][j]>a.ans[i][k]+b.ans[k][j]&&a.ans[i][k]+b.ans[k][j]>0 )K.ans[i][j]=a.ans[i][k]+b.ans[k][j];a=K;
}void MatrixXmult( int k,Floyd &pre ) 
{Floyd now1=pre;Floyd now2=pre;if( k<=1 ) return ;else if( k%2==0 ){MatrixXmult( k>>1,now1 );Matrix2( now1,now1 );}else if( k%2==1 ){MatrixXmult( k-1,now1 );Matrix2( now1,now2 );}pre=now1;
}int main()
{while( scanf( "%d %d %d %d",&N,&T,&S,&E )!=EOF ){int i,u,v,price;bool inCow[1001];memset( inCow,0,sizeof(inCow) );int hash[1001];memset( hash,0,sizeof(hash) );for( i=1;i<=T;i++ ){scanf( "%d %d %d",&edge[i].price,&edge[i].u,&edge[i].v );inCow[ edge[i].u ]=true;inCow[ edge[i].v ]=true;}cnt=0;for( i=1;i<=1000;i++ ){if( inCow[i] )hash[i]=++cnt;}memset( YB.ans,0x7F,sizeof(YB.ans) );for( i=1;i<=T;i++ ){YB.ans[ hash[ edge[i].u ] ][ hash[ edge[i].v ] ]=edge[i].price;YB.ans[ hash[ edge[i].v ] ][ hash[ edge[i].u ] ]=edge[i].price;}MatrixXmult( N,YB );printf( "%d\n",YB.ans[hash[S]][hash[E]] );}return 0;
}