穷举查找之旅行商问题、背包问题、分配问题

穷举查找

对于组合问题来说,穷举查找是一种简单的蛮力算法。它要求生成问题域中的每一个元素,选出其中满足问题约束的元素,然后再找出一个期望元素。

旅行商问题

简单来说,这个问题要求找出一条n个给定的城市间的最短路径,使我们在回到出发的城市之前,对每个城市都只访问一遍。这个问题可以很方便地用加权图来建模,也就是说,用图的顶点代表城市,用边的权重表示城市间的距离。这样该问题就可以表述为求一个图的最短哈密顿回路问题。

哈密顿回路:一个对图的每个顶点都只穿越一次的回路

对于四个点都连通的图,我们假定从a点出发,可以将获得(4-1)!条路径(公式(n-1)!),但是需要注意的是,如果没有假定起点,那么这个问题的规模将增大n倍
在这里插入图片描述
对于图中的例子,其实我们发现它们是两两成对的,同对之间不同的仅仅是方向,因此,我们可以将路径总数减半(n-1)!/2,但是,显然,这并没有提高太大的效率。

背包问题

这是计算机科学中另一个著名的问题。给定n个重量为 w 1 , w 2 , . . . , w n , w_1,w_2,...,w_n, w1,w2,...,wn,价值为 v 1 , v 2 , . . . , v n v_1,v_2,...,v_n v1,v2,...,vn的物品和一个承重为W的背包,求这些物品中一个最优价值的子集,并且要能够装到背包中。
在这个问题中,穷举查找需要考虑给定的n个子集,为了找出可行的子集(也就是说,总重量不超过背包承重能力的子集),要计算出每个子集的总重量,然后在它们中间找到价值最大的子集。因为一个n元素集合的子集数量为 2 n 2^n 2n个,所以无论生成独立子集的效率有多高,穷举查找都会导致一个 Ω ( 2 n ) \Omega(2^n) Ω(2n)的算法。如下例子:
在这里插入图片描述

因此无论是对旅行商问题还是背包问题,穷举查找型算法对于任何输入都是非常低效的。实际上,这两个问题就是所谓的NP困难问题中最著名的例子。

分配问题

对于可以穷举查找求解的问题,我们再举第三个例子:有n个任务需要分配给n个人执行,一个任务对应一个人(意思是说:每个任务只分配一个人,每个人只分配一个任务)。对于每一对i,j=1,2,…,n来说,将第j个任务分配给第i个人的成本是C[i,j],该问题要找出总成本最小的分配方案。
下面是该问题的一个小规模的实例,表中的数值代表的是分配成本C[i,j]
在这里插入图片描述
很容易发现,分配问题的实例完全可以用它的成本矩阵C来表示。就这个矩阵来说,这个问题要求在矩阵的每一行中选出一个元素,这些元素分别属于不同的列,而且元素的和是最小的。请注意,求解该问题并没有一个显而易见的策略。例如,我们不能选择每行中的最小元素,因为这些元素可能属于同一列。实际上,整个矩阵的最小元素并不一定是最优解的一部分。下面是上面例子的答案:
在这里插入图片描述

由于在分配问题的一般情况下,需要考虑的排列数量是n!,所以除了该问题的一些规模非常小的实例,穷举查找法几乎不实用。幸运的是,对于该问题有一个效率高得多的算法,叫匈牙利方法。

笔者打算先把穷举的情况先了接了,再深入后面的改良,穷举算法的改进版后续会再做补充

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

绿豆蛙给生活加点甜

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值