ABC369E
题解
看到 floyd 来求全源最短路,求出每两个点之间的最短路。
但我们发现会有重边,便考虑取两点的最小边,取最小值。
接着是必须经过
时间复杂度:
#include<bits/stdc++.h>
using namespace std;
long long a[505][505],k,p[50005],ans=1e18,bz[500005];
long long n,m;
struct edge
{
long long u,v,w;
}e[500005];
void dfs(long long t,long long sum,long long now)
{
if(t==k+1)
{
ans=min(ans,sum+a[now][n]);
return ;
}
for(int i=1;i<=k;i++)
{
if(bz[i]==0)
{
bz[i]=1;
dfs(t+1,sum+a[now][e[p[i]].u]+e[p[i]].w,e[p[i]].v);
dfs(t+1,sum+a[now][e[p[i]].v]+e[p[i]].w,e[p[i]].u);
bz[i]=0;
}
}
}
int main()
{
cin>>n>>m;
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
{
a[i][j]=1e18;
}
for(int i=1;i<=n;i++)a[i][i]=0;
for(int i=1;i<=m;i++)
{
cin>>e[i].u>>e[i].v>>e[i].w,a[e[i].u][e[i].v]=min(e[i].w,a[e[i].u][e[i].v]),a[e[i].v][e[i].u]=min(a[e[i].v][e[i].u],e[i].w);
}
for(int k=1;k<=n;k++)
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
{
if(a[i][j]>(a[i][k]+a[k][j])) a[i][j]=a[i][k]+a[k][j];
}
long long q;
cin>>q;
while(q--)
{
ans=1e18;
cin>>k;
for(int i=1;i<=k;i++)cin>>p[i];
dfs(1,0,1);
cout<<ans<<'\n';
}
}