TSP问题
给你n个城市和城市之间的通路的长度,请你找出一条经过所有城市一次且仅经过一次的路线,使得这条路线的长度最短。
问题分析,如果要设计一个状态的话,显然状态与已经走过的城市和你当前所在的城市有关,现在,按照一定的顺序给每个城市一个编号,如果已经走过的城市记为1,没走过的城市记为0,那么已经走过的城市的状态就可以压缩成一个数。所以,该题目的状态表示为:
i=5~000101表示点1和点3已被访问
dp[i][j]表示分析在当前的状态i下,路径都为已经访问过的城市,找一条最短路径到达的j的总距离
相应的状态转移方程为dp[ i ][ j]=min( dp[ i ^ (1<
i ^ (1<
TSP基础问题
memset(dp, inf, sizeof(dp));
for (int i = 1; i <= n; i++)
dp[1<<(i - 1)][i] = 0;
int ans = inf;
for (int i = 0; i < (1<
2 1
1 2 100
3 2
1 2 40
2 3 50
3 3
1 2 3
1 3 4
2 3 10
Sample Output
100
90
7
题意:n个点m条边,求某个点出发所有城市都要到达,每个城市最多可以被访问2次,求最短距离
题解:使用3进制存储状态:0,1,2次访问
#include
#include
#include
#include
#include
#include
#define inf 0x3f3f3f3f
#define ll long long
using namespace std;
int w[20][20];
int dp[60000][20];
int bit[12] = {0,1, 3, 9, 27, 81, 243, 729, 2187, 6561, 19683, 59049};//0001,0010,0100,1000...对应的十进制数
int num[60000][20];//某个十进制数的3进制形式存入num
int n,m;
void make_bit()
{
for(int i=1;i<59050;i++)
{
int n=i,j=1;
while(n)
{
num[i][j++]=n%3;
n=n/3;
}
}
}
int main()
{
make_bit();
while(cin>>n>>m)
{
memset(w,-1,sizeof(w));
for(int i=1;i<=m;i++)
{
int a,b,c;
cin>>a>>b>>c;
if(w[a][b]==-1)
w[a][b]=w[b][a]=c;
else
w[a][b]=w[b][a]=min(w[a][b],c);//防止出现重边
}
memset(dp,inf,sizeof(dp));
for(int i=1;i<=n;i++)
dp[bit[i]][i]=0;
int ans=inf;
for(int i=1;i