【实验目的】
1、掌握回溯法的设计思想;
2、掌握解空间树的构造方法,以及在求解过程中如何存储求解路径;
3、考察回溯法求解问题的有效程度。
TSP问题
一、实验内容:
利用回溯法编程求解TSP问题。
回溯算法的基本思想是:从一条路往前走,能进则进,不能进则退回来,换一条路再试。
用回溯算法解决问题的一般步骤为:
1、定义一个解空间,它包含问题的解。
2、利用适于搜索的方法组织解空间。
3、利用深度优先法搜索解空间。
4、利用剪枝函数避免移动到不可能产生解的子空间
对于n=4的TSP问题,其解空间树如图所示,树中的24个叶子结点分别代表该问题的24个可能解,例如结点5代表一个可能解,路径为1→2→3→4→1,长度为各边代价之和。
算法搜索至解空间树的任一结点时,总是先判断该结点是否肯定不包含问题的解。如果肯定不包含,则跳过对以该结点为根的子树的系统搜索,逐层向其祖先结点回溯。否则,进入该子树,继续按深度优先的策略进行搜索。回溯法在用来求问题的所有解时,要回溯到根,且根结点的所有子树都已被搜索遍才结束。而回溯法在用来求问题的任一解时,只要搜索到问题的一个解就可以结束。
二、实验源程序及结果截图:
1、实验代码:
#include <iostream>
using namespace std;
#define N 25
int n;//城市个数
int d[N+1][N+1]; //邻接矩阵
int x[N];//存放顶点号
int best[N]; //最优路径
int len_now; //当前路径长度
int length=100;//最优距离
void TSP(int t)
{
if(t>n) //到叶子节点
{
//如果最后一个城市与出发的城市之间有路径,且当前总距离比最优值小,则更新最优值
if(d[x[n]][x[1]] > 0 && len_now+d[x[n]][x[1]] < length || length==0)
{
length=len_now+d[x[n]][x[1]];
for(int j=1; j<=n; j++)
best[j]=x[j];
cout<<"目前最优解为:"<<endl;
for(int j=1; j<=n; j++)
cout<<best[j]<<" ";
cout<<best[1];
cout<<"\n距离为:"<<length<<endl;
}
}
else //没有搜索到叶子节点
{
for(int i=t;i<=n;i++)
{
//如果第t-1个城市与第i个城市之间有路径,且当前总距离比最优值小,则更新最优值
if(d[x[t-1]][x[i]