题目
找一个最小环
1-2-5-3-1 16+15+20+10=61
分析(1)
这道题用floyd,找最小值
伪代码
for (int k=1;k<=n;k++){
for (int i=1;i<k-1;i++)
for (int j=i+1;j<k;j++)
ans=min(ans,dis[i][j]+a[i][k]+a[k][j]);//寻找最小环
for (int i=1;i<=n;i++)
for (int j=1;j<=n;j++)
if (dis[i][j]>dis[i][k]+dis[k][j]) dis[i][j]=dis[i][k]+dis[k][j];//floyd正常过程
}
floyd代码(1)
#include <cstdio>
#include <cctype>
#include <algorithm>
#include <cstring>
using namespace std;
int n,m,a[101][101],x,y,ans=2147483647,dis[101][101];
int in(){
int ans=0; char c=getchar();
while (!isdigit(c)) c=getchar();
while (isdigit(c)) ans=ans*10+c-48,c=getchar();
return ans;
}
int main(){
n=in(); m=in(); memset(dis,127/3,sizeof(dis)); memset(a,127/3,sizeof(a));
for (int i=1;i<=m;i++) a[x=in()][y=in()]=a[y][x]=dis[x][y]=dis[y][x]=in();
ans=dis[0][0];
for (int k=1;k<=n;k++){
for (int i=1;i<n;i++)
for (int j=i+1;j<=n;j++)
ans=min(ans,dis[i][j]+a[i][k]+a[k][j]);
for (int i=1;i<=n;i++)
for (int j=1;j<=n;j++)
if (dis[i][j]>dis[i][k]+dis[k][j]) dis[i][j]=dis[i][k]+dis[k][j];
}
if (ans!=dis[0][0]) printf("%d",ans);//没找到
else puts("No solution");
return 0;
}
分析(2)
使用枚举+dijkstra的方法
删掉一条边,求这条边的一个点到另一个点的最短路径,最短路径加上这条边的权值为答案。
16+15+20+10=61
dijkstra代码
#include <cstdio>
#include <cctype>
#include <cstring>
using namespace std;
int n,m,x,y,mins; bool v[101];
int low[101],a[101][101];
int in(){
int ans=0; char c=getchar();
while (!isdigit(c)) c=getchar();
while (isdigit(c)) ans=ans*10+c-48,c=getchar();
return ans;
}
int main(){
n=in(); m=in(); memset(a,127/3,sizeof(a)); mins=a[0][0];
for (int i=1;i<=m;i++) a[x=in()][y=in()]=a[y][x]=in();
for (int y=2;y<=n;y++)
for (int x=1;x<y;x++)
if (a[x][y]!=a[0][0]){//可以通行
int t=a[x][y]; a[x][y]=a[y][x]=a[0][0];//删掉
for (int i=1;i<=n;i++) low[i]=a[x][i];
memset(v,0,sizeof(v)); v[x]=1;
for (int i=1;i<n;i++){//dijkstra
int min=a[0][0],k=0;
for (int j=1;j<=n;j++)
if (!v[j]&&min>low[j]) min=low[j],k=j;//求最小边
if (!k) break; v[k]=1;
for (int j=1;j<=n;j++) if (!v[j]&&low[j]>low[k]+a[k][j]) low[j]=low[k]+a[k][j];//更新
}
mins=mins>(low[y]+t)?(low[y]+t):mins; a[x][y]=a[y][x]=t;
}
if (mins!=a[0][0]) printf("%d",mins); else puts("No solution");
return 0;
}