旅行商问题——贪心算法

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/fancynece/article/details/79455821

旅行商问题(TSP)

旅行商问题是一个经典的组合优化问题。

经典的TSP问题可以描述为:一个商品推销员要去若干个城市进行商品推销,该推销员从一个城市出发,需要经过所有城市,回到出发地。应如何选择行进路线,以使总的行程最短。

从图论的角度来看,该问题实质是在一个带权完全无向图中,找一个权值最小的Hamilton回路。

由于该问题的可行解是所有顶点的全排列,随着顶点数的增加,会产生组合爆炸。

在这里我们以贪心算法来解决这个问题,当数据规模越大时,以近似解来替代最优解。

#include <iostream>
#include <assert.h>

using namespace std;

#define MAX 1000000
#define n 4

int D[n][n]; //记录两城市间距离
int S[n];    //记录第i次去的城市

void Init()
{
    for (int i = 0; i < n; ++i)
        for (int j = i; j < n; ++j)
            D[i][j] = D[j][i] = MAX;

    for (int i = 0; i < n; ++i)
        S[i] = -1;

}

bool checkAccess(int city)
{   
    //判断该城市是否访问过
    for (int i = 0; i < n; ++i)
        if (S[i] == city)
            return true;
    return false;
}

int findCity(int city)
{
    //查找下一次要去的距离最短的城市
    int min = MAX;
    int nextCity;

    for (int i = 0; i < n; ++i)
        if (D[city][i] < min && checkAccess(i) == false)
        {
            min = D[city][i];
            nextCity = i;
        }

    return nextCity;
}

void TSP(int start)
{
    S[0] = start;

    size_t sum = 0;

    for (int i = 1; i < n; ++i)
    {
        S[i] = findCity(S[i - 1]);
        sum += D[S[i - 1]][S[i]];
    }

    printf("访问顺序为:");

    for (int i = 0; i < n; ++i)
        printf("%d", S[i]);

    printf("\n");

    printf("总距离为:%d", sum);

}

int main()
{

    int i, j, k;

    Init();   //初始化距离数组和访问数组

    /*while (scanf("%d%d%d",&i,&j,&k) != EOF)
    {
        assert(i >= 0 && j >= 0 && k > 0 && i != j);

        D[i][j] = D[j][i] = k;
    }*/

    D[0][1] = D[1][0] = 2;
    D[0][2] = D[2][0] = 6;
    D[0][3] = D[3][0] = 5;
    D[1][2] = D[2][1] = 4;
    D[1][3] = D[3][1] = 4;
    D[2][3] = D[3][2] = 2;

    TSP(0);

    getchar();

    return 0;
}

猜你喜欢

转载自blog.csdn.net/fancynece/article/details/79455821