TSP:旅行商问题与内存优化的动态规划

文章探讨了如何利用动态规划解决旅行商问题(TSP),特别是针对25个点的大规模实例。通过优化回路处理、BFS层次遍历、visit数组和dp数组,降低了时间和空间复杂度。提出的状态压缩和层次遍历策略能够有效减少内存需求,同时保持算法的正确性。
摘要由CSDN通过智能技术生成

旅行商问题(TSP)是著名的NP问题,最暴力的做法是枚举点的排列,因此时间复杂度是O(n!).

一种较好的精确算法是动态规划,时间复杂度是O(n22n).


最近遇到了使用动态规划求25个点的TSP问题,浮点数输入,精确解输出.

这个数据在时间和空间上都很糟糕,尤其是空间,原始的算法占用内存过大.

于是和一些同学进行了讨论,把得到的想法思路在此整理一下.


基本框架

用动态规划做TSP,就是在一个有向无环图(DAG)上做dp,图上的每个节点是一个二元组的状态(i,S),对应一条路径.

其中i表示当前路径的最后一个点,S是一个集合,表示路径上的点集.

那么,每个状态(i,S)的所有前驱(j,S'),一定会满足:

j∈S且S=S'+{i}

递推方程为:

dp(i,S)=min(dp(j,S-{i})+cost(i,j)) , j∈S且j≠i

方程的简单理解就是,到j的最短距离,加上j到i的最短距离,就是对应的i的最短距离.


集合S在具体实现上要映射到一个数字,我们可以用二进制串的状态压缩.

一个二进制串的第i位就表示第i个点是否在S里,为1表示在,为0表示不在.


每个状态需要枚举j,因此时间上是O(n).状态一共有O(n2n)个(包含一些非法状态),因此总的时间复杂度是O(n22n).

而空间复杂度,最占空间的dp数组需要O(n2n)的空间,因此空间复杂度是O(n2n).


回路处理

由于TSP要求的是一个最短的回路,即起点终点为同一个点.

由于是回路,因此设哪个点是起点其实没有所谓,简单起见,不妨设第n-1个点为起点(下标从0开始).

这样处理后,在dp过程中,可以完全不考虑第n-1个点,然后适当处理一下dp的开头和结尾.

dp的初始化为:

dp(i,{i})=cost(i,n-1) , i∈[0,n-1)

dp最后的答案为:

min(dp(i,Sfull)+cost(i,n-1)) , i∈[0,n-1) , Sfull={0,1,2,...n-2}

这样处理dp(i,S)的含义就是从n-1为起点,经过了S里面的点,并且最后到达i的最短距离.

Sfull这个状态就表示所有的点都经过了一遍,就差回

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值