老师讲解是:
1、先预处理出以1、a、b、c、d、e出发到其他所有点的单源最短路径。
2、DFS所有拜访顺序,(5!),对于每一种摆拜访顺序,可以通过查表的方式,算出最短距离。
我:
极其讨厌dfs的我直接放弃选择枚举。
代码实现:
#include<bits/stdc++.h>
#define N 50000+10
using namespace std;
int n,m,peo[10];
int a[10][10],d[N],used[N];
int ans=1e9;
vector<int>v[N];
vector<int>val[N];
void spfa(int id,int st){
queue<int>q;
memset(d,0x3f,sizeof d);
memset(used,0,sizeof used);
d[st]=0,used[st]=1;
q.push(st);
while(q.size()){
int x=q.front();q.pop();
used[x]=0;
for(int i=0;i<v[x].size();i++){
int y=v[x][i],z=val[x][i];
if(d[y]>d[x]+z){
d[y]=d[x]+z;
if(!used[y]){
q.push(y);used[y]=1;
}
}
}
}
for(int i=1;i<=6;i++)
a[id][i]=d[peo[i]];
}
int main(){
scanf("%d%d",&n,&m);
for(int i=2;i<=6;i++)
cin>>peo[i];
peo[1]=1;
for(int i=1;i<=m;i++){
int x,y,z;
scanf("%d%d%d",&x,&y,&z);
if(x==y)continue;
v[x].push_back(y);
val[x].push_back(z);
v[y].push_back(x);
val[y].push_back(z);
}
for(int i=1;i<=6;i++)
spfa(i,peo[i]);
for(int p1=2;p1<=6;p1++)
for(int p2=2;p2<=6;p2++)
for(int p3=2;p3<=6;p3++)
for(int p4=2;p4<=6;p4++)
for(int p5=2;p5<=6;p5++){
if(p1==p2||p1==p3||p1==p4||p1==p5||p2==p3||p2==p4||p2==p5||p3==p4||p3==p5||p4==p5)continue;
int cnt=a[1][p1]+a[p1][p2]+a[p2][p3]+a[p3][p4]+a[p4][p5];
ans=min(ans,cnt);
}
cout<<ans;
return 0;
}