【模版 Floyd最小环】
输入
输入中有多组数据。请用SeekEof判断是否到达文件结束。
对于每组数据:
第一行有两个正整数N,M,分别表示学校的景点个数和有多少对景点之间直接有边相连。(N< =100,M< =10000)
以下M行,每行三个正整数,分别表示一条道路的两端的编号,以及这条道路的长度。
输出
对于每组数据,输出一行:
如果该回路存在,则输出一个正整数,表示该回路的总长度;否则输出“No solution.”(不要输出引号)
样例输入
5 7 1 4 1 1 3 300 3 1 10 1 2 16 2 3 100 2 5 15 5 3 20 4 3 1 2 10 1 3 20 1 4 30
样例输出
61 No solution.
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<algorithm> 5 using namespace std; 6 int gi(){ 7 int str=0;char ch=getchar(); 8 while(ch>'9' || ch<'0')ch=getchar(); 9 while(ch>='0' && ch<='9')str=(str<<1)+(str<<3)+ch-48,ch=getchar(); 10 return str; 11 } 12 const int N=105; 13 int n,m,dis[N][N],w[N][N]; 14 void work() 15 { 16 int x,y,z; 17 memset(dis,127/3,sizeof(dis)); 18 memset(w,127/3,sizeof(w)); 19 for(int i=1;i<=m;i++) 20 { 21 x=gi();y=gi();z=gi(); 22 w[x][y]=w[y][x]=z; 23 dis[x][y]=dis[y][x]=z; 24 } 25 int ans=2e8; 26 for(int k=1;k<=n;k++) 27 { 28 for(int i=1;i<=k-1;i++) 29 for(int j=i+1;j<=k-1;j++) 30 ans=min(ans,w[i][k]+w[k][j]+dis[i][j]); 31 for(int i=1;i<=n;i++) 32 for(int j=1;j<=n;j++) 33 if(i!=j && j!=k && i!=k && dis[i][k]+dis[k][j]<dis[i][j])dis[i][j]=dis[i][k]+dis[k][j]; 34 } 35 if(ans==2e8)printf("No solution.\n"); 36 else printf("%d\n",ans); 37 } 38 int main() 39 { 40 while(~scanf("%d%d",&n,&m)) 41 work(); 42 return 0; 43 }