TSP 动态规划

TSP问题

Time Limit: 5000 ms     Memory Limit: 65535 KB
Total Submit: 163     Accepted: 83 

Description
旅行商问题,即TSP问题(Travelling Salesman Problem)又译为旅行推销员问题、货郎担问题,是数学领域中著名问题之一。假设有一个旅行商人要拜访n个城市,他必须选择所要走的路径,路径的限制是每个城市只能拜访一次,而且最后要回到原来出发的城市。路径的选择目标是要求得的路径路程为所有路径之中的最小值。

Input
第一行输入一个整数n(2<=n<=15)。
接下来的n行,每行输入n-1个整数xj(0<xj<=500),表示i与除了自己之外的所以点之间的距离,按点的编号从小到大的顺序输入。

Output
输出一行,就是所有路径之中的最小值。

Sample Input
5
3 1 5 8
3 6 7 9
1 6 4 2
5 7 4 3
8 9 2 3
4
3 6 7
5 2 3
6 4 2
3 7 5

Sample Output
16
10



这段代码的集合使用二进制来表示的,需要注意的就是集合的枚举顺序。由于是用二进制表示的,则可以发现这样一个规律,如果a是b的真子集,则相对应的二进制数一定有a<b。因此若以集合递增的顺序计算,需要用到某个d值是,它一定是在之前已经计算出来的。


#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <string>
#include <vector>
#include<map>
#define pi acos(-1.0)
#define eps 1e-6
#define inf 1<<30
#define INF 1ll<<60
#define ll long long
using namespace std;
int n;
int maps[20][20];
int d[20][1<<16];
int main()
{
    int a;
    while(cin>>n)
    {
        for(int i=0; i<n; i++)
        {
            for(int j=0; j<n; j++)
            {
                if(i==j)
                {
                    maps[i][i]=inf;
                    continue;
                }
                int a;
                cin>>a;
                maps[i][j]=a;
            }
        }
        for(int i=0; i<n; i++)
            for(int s=0; s<(1<<n); s++)
                d[i][s]=inf;
        for(int s=0; s<(1<<n-1); s++)
        {

            for(int i=0; i<n; i++)
            {
                 if(s==0)
                d[i][s]=maps[i][0];
                for(int j=1; j<n; j++)
                {
                    if(s&(1<<(j-1)))
                        d[i][s]=min(d[i][s],d[j][s^(1<<(j-1))]+maps[i][j]);
                }
            }
        }
//        for(int i=0; i<n; i++)
//        {
//            for(int s=0; s<(1<<(n-1)); s++)
//
//                cout<<d[i][s]<<" ";
//            cout<<endl;
//        }
        cout<<d[0][(1<<n-1)-1]<<endl;
    }
    return 0;
}




发布了40 篇原创文章 · 获赞 3 · 访问量 2万+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章