【问题简述】
给出N个城市和M条带权无向边,求从1到N在必须经过给定的T个城市的前提下的最短路长度。
【输入】
第一行:n,m,t,表示城市数,道路数,必须经过的城市数
第二行:t个整数,表示必经的城市
接下来m行,每行3个整数,前两个表示城市,第三个数是这两个城市间的直达时间
【输出】
一个数,最短时间
【数据范围】
n<=200,m<=20000,直达时间<=1000000
【时限】
5s
【样例输入】
5 10 2
2 3
1 2 5
1 3 45
1 4 61
1 5 81
2 3 9
2 4 91
2 5 4
3 4 74
3 5 42
4 5 61
【样例输出】
27
【问题分析】
floyd(或t+1次单源最短路径)+搜索排列
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#define MAXN 210 #define oo ((LL)1000000*20000+10) using namespace std; typedef long long LL; LL MIN(LL x,LL y){ return x
g[MAXN],w[MAXN]; LL d[MAXN][MAXN]; void floyd() { for(int i=1;i<=N;i++) for(int j=1;j<=N;j++) d[i][j]=i==j?0:oo; for(int i=1;i<=N;i++){ for(int k=0;k
T){ ans=MIN(ans,len+d[j][N]); return; } for(int x=1;x<=T;x++)if(vis[x]==0){ vis[x]=1; LL t=len+d[j][must[x]]; run(i+1,must[x],t); vis[x]=0; } } int main() { cin>>N>>M>>T; for(int i=1;i<=T;i++) scanf("%d",must+i); for(int i=1;i<=M;i++){ int a,b,c; scanf("%d%d%d",&a,&b,&c); g[a].push_back(b); w[a].push_back(c); g[b].push_back(a); w[b].push_back(c); } floyd(); ans=oo; memset(vis,0,sizeof(vis)); run(1,1,0); cout<
<