先用floyd求出最短路,然后用状态压缩dp求出
状态压缩dp和坐标搜寻差不多
#include<iostream> #include<algorithm> #include<cstring> #include<vector> #include<cmath> using namespace std ; const int N = 20 ; double INF = 1e9; double f[1<<N][N] ; double w[N][N] ; int n ; double d ; double x[N] , y[N] ; double dis(int a,int b ){ return sqrt((x[a] - x[b])*(x[a] - x[b]) + ((y[a] - y[b]) *(y[a] - y[b] ))) ; } void floyd(){ for(int k = 0 ; k < n ; k ++){ for(int i = 0 ; i < n ; i++){ for(int j = 0; j < n ; j ++){ w[i][j] = min(w[i][j] , w[i][k] + w[k][j]) ; } } } } int main(){ cin >> n >> d ; for(int i = 0 ; i < n ; i++){ cin >> x[i] >> y[i] ; } for(int i = 0 ; i < n ; i ++){ for(int j = 0 ; j < n ;j ++){ w[i][j] = w[j][i] = dis(i,j) ; if(w[i][j] > d) w[i][j] = w[j][i] = INF ; } } floyd() ; memset(f,127,sizeof(f)) ; f[1][0] = 0 ; for(int s = 0 ; s < 1 << n ; s ++){ for(int i = 0 ; i < n ; i ++){ if(((s >> i) & 1)) for(int j = 0 ; j < n ; j ++){ if((s ^(1<<i)) >> j & 1){ f[s][i] = min(f[s][i], f[s ^(1<<i)][j] + w[j][i]) ; } } } } double res = INF; for(int i = 1 ; i < n ;i ++) { res = min (f[(1<<n)-1][i] + w[i][0], res ) ; } printf("%.2f",res); }