算法的故事 / 第一季第二季目录0 / 30 章已读

第二季 · 第 40 章

不可能完成的旅行

《算法的故事》第二季 · 第二篇:寻找世界的最优解——克里斯托菲德斯与一个允许不完美的算法1976年4月,美国宾夕法尼亚州匹兹堡。卡内基梅隆大学正在筹备一场关于算法与计算复杂性的学术会议。会议日程中,有一项研究的题目十分引人注目:《旅行商问题一种新启发式方法的最坏情况分析》。作者是一位来自帝国理工学院、当时正在卡内基梅隆大学访问的研究者。他的名字叫尼科斯·克里斯托菲德斯(Nicos Christofides)。他研究的问题,似乎每个经常出差的人都能够理解。假设一名推销员需要访问许多座城市。每座城市都必须去一次,最后还要回到出发地点。他希望整个旅程尽可能短。五座城市。十座城市。五十座城市。问题听起来不过是寻找一条更合理的旅行路线。然而,城市的数量越多,可能的访问顺序就越惊人。计算机可以很快计算两座城市之间的距离。但要证明某一条环游路线是所有路线中最短的一条,可能需要难以想象的搜索工作。即使最优秀的数学家,也无法让任意巨大规模的问题都轻松获得精确最优解。克里斯托菲德斯于是改变了提问方式。他不再坚持每次都必须找到绝对最短路线。他想知道:能不能设计一种计算足够高效的算法,即使偶尔找不到最优路线,也能从数学上保证,它绝对不会比最优路线长得太离谱?他的答案令人惊讶。只需要把三项看似不同的图论工具组合起来:一棵最小生成树。一次最小权完美匹配。一条欧拉回路。然后再做一个小小的动作——跳过重复访问的城市。对于满足三角不等式的对称旅行商问题,这套算法能够保证:算法路线长度≤1.5×真正的最短路线长度\boxed{\text{算法路线长度}\le1.5\times\text{真正的最短路线长度}}这意味着,即使我们不知道真正的最优路线是什么,也能够对自己计算出来的方案给出严格的质量保证。它并不承诺完美。但它能够证明,自己离完美不会超过一个明确的界限。这就是 Christofides 算法的故事。也是我们第二篇《寻找世界的最优解》的最后一章。

第一幕:一位旅行者,为什么会让计算机束手无策?

二十世纪中期的公路旅行环境。旅行商问题的实际来源可以追溯到更早的路线规划需求,但现代数学研究关注的是更一般的组合优化结构。假设你准备驾驶汽车,前往六座城市进行拜访。你可以从任意一座城市出发。但所有城市都必须访问。最后,还要回到原点。为了避免重复行驶,你规定每座城市只作为一次正式停靠点。这样的一条路线,在图论中叫作哈密顿回路(Hamiltonian Cycle)。我们要找到的,是所有哈密顿回路中总距离最短的那一条。这就是旅行商问题:Travelling Salesman Problem,通常缩写为 TSP。

六座城市,已经有多少种旅行方式?

假设有六座不同的城市。我们把第一座城市固定为出发点。剩下五座城市,可以按照任意顺序排列。于是,共有:5!=1205!=120种访问顺序。但如果道路距离是对称的,那么:从A经过B、C、D再回到A,与按照反方向经过D、C、B再回到A,其总长度相同。因此,在忽略起点和行驶方向所造成的重复后,六座城市有:(6−1)!2=60\frac{(6-1)!}{2}=60种不同的环游路线。六十种。听起来并不算多。如果每种路线都计算一遍距离,或许很快就能找到最短的。但是,假如增加到十座城市:9!2=181440\frac{9!}{2}=181440再增加到二十座城市:19!2≈6.08×1016\frac{19!}{2}\approx6.08\times10^{16}如果有五十座城市:49!2≈3.04×1062\frac{49!}{2}\approx3.04\times10^{62}
图40-1:路线组合数量的爆炸式增长
城市数量不同环游路线数量
512
660
10181,440
15约436亿
20约6.08×10¹⁶
50约3.04×10⁶²
假设所有城市均需访问,起点固定,且路线反向等价。这些是搜索空间的数量,不是某个具体求解器一定需要检查的路线数。
这里要特别注意最后一句话。可能的路线数量极其庞大,并不意味着所有精确算法都必须真的把全部路线检查一遍。数学家可以利用动态规划、分支定界、线性规划松弛和割平面方法,避免大量无意义的搜索。许多规模可观的实际旅行商问题,也确实已经被精确求解。但这些方法并没有消除问题在一般情况下的计算困难。如果城市规模不断增大,我们仍然需要考虑:怎样在有限的计算资源之内,获得可靠的路线?

一个源于现实、又超出现实的数学问题

旅行商问题的现代数学研究,通常会追溯到二十世纪初。奥地利数学家 卡尔·门格尔(Karl Menger)在1930年前后讨论过类似的访问路线问题。到了1930年代,这类问题又出现在普林斯顿的数学研究圈中。哈斯勒·惠特尼(Hassler Whitney)曾提出访问美国各州城市的最短旅行路线问题。二十世纪四五十年代,随着运筹学和计算机的发展,旅行商问题逐渐成为组合优化研究的重要对象。[JSTOR][滑铁卢大学数学系]

1954年,丹齐格和富尔克森又出现了

1954年丹齐格、富尔克森与约翰逊所研究的美国49城市旅行商路线。其历史成果由 Waterloo 大学旅行商问题研究网站保存并介绍。在第36章,我们认识了发明单纯形法的乔治·丹齐格。在第37章,我们认识了研究最大流的雷·富尔克森。现在,这两位数学家再次出现在同一个故事里。1954年,丹齐格、富尔克森与塞尔默·约翰逊(Selmer Johnson)共同发表论文:Solution of a Large-Scale Traveling-Salesman Problem。《一个大规模旅行商问题的求解》。他们研究了一条涉及美国当时48个州各选一座城市,再加上华盛顿特区,共49座城市的公路旅行路线。利用线性规划与割平面思路,他们证明了特定路线在所用距离数据下的最优性。这在当时是一项令人瞩目的计算成就。[PubsOnLine][滑铁卢大学数学系]但它也提出了一个新问题。对于49个城市,数学家已经能够通过精巧的计算得到一个严格最优解。如果有几百座、几千座,甚至几十万座呢?我们是否仍然应该坚持每次都寻找精确最优?还是说,可以接受一个足够好的近似答案?这项思考,将问题引向另一种算法思想。

第二幕:1976年,克里斯托菲德斯改变了目标

尼科斯·克里斯托菲德斯(1942—2019)。他长期在帝国理工学院从事运筹学、组合优化和金融数学研究。[Imperial Business School]尼科斯·克里斯托菲德斯1942年出生于塞浦路斯。他年轻时前往英国求学。1960年,他获得奖学金,进入伦敦帝国理工学院学习电气工程。1966年,他以优异成绩毕业,随后完成博士研究。他的博士工作涉及感应电动机中的损耗问题。之后,他逐渐转向组合优化与图论。1968年,他开始在帝国理工学院任教,并与 Samuel Eilon 等研究人员共同推动车辆路径规划领域的发展。他的研究兴趣横跨工程、数学和实际运输问题。[Imperial Business School]

餐桌上的英国公路地图

帝国理工学院后来发表的悼念文章,留下了一段很有生活气息的回忆。克里斯托菲德斯的儿子们记得,在他们小时候,家里的餐桌曾长时间摆满地图、彩色笔和描图纸。父亲与母亲安(Ann)利用晚间时间,将英国道路系统的资料整理成数字数据。这项工作可能持续了数月,甚至数年。这不是一段经过文学虚构的科学家对话,而是其家人在官方悼念文章中提供的回忆。[Imperial Business School]这段细节尤其值得记住。因为它说明,克里斯托菲德斯并不是只在黑板前研究抽象的点和线。他也面对真实道路网络。真实地理数据。真实路线所带来的工程限制。算法最终能否帮助人类安排更好的行程,对他而言并非一个无关紧要的问题。根据家属回忆重构的研究场景:纸质地图、描图纸和标记工具。此图并不是克里斯托菲德斯家中餐桌的原始照片。

一次从英国前往美国的学术访问

1975年,他出版了《Graph Theory: An Algorithmic Approach》。《图论:一种算法方法》。这是一部与他长期研究方向密切相关的著作。此后,他赴北美进行学术访问。1976年春天,卡内基梅隆大学举办了关于算法与复杂性理论的学术会议。保留下来的会议日程显示:克里斯托菲德斯以卡内基梅隆大学访问研究者、帝国理工学院休假教师的身份,被列入会议报告安排。报告题目是:Worst-Case Analysis of a New Heuristic for the Travelling Salesman Problem。这份1976年会议资料,如今仍保存在卡内基梅隆大学档案中。与此同时,1976年,他的同名研究以卡内基梅隆大学管理科学研究报告第388号的形式传播。那篇论文的核心目标十分明确。此前,对于满足三角不等式的旅行商问题,人们已经拥有能够保证不超过最优路线两倍长度的多项式时间算法。克里斯托菲德斯希望进一步改善这个最坏情况保证。他最终将界限从2降到了:32\boxed{\frac32}也就是1.5。[Google Books][Springer Nature Link]

这里的“最坏情况”,到底是什么意思?

假设真正的最短路线长度为:OPTOPT某种算法找到的路线长度为:ALGALG对于一个求最短路线的问题,我们总有:ALG≥OPTALG\ge OPT因为任何合法路线,都不可能比真正最短的路线更短。如果能够证明:ALG≤1.5 OPTALG\le1.5\,OPT那么,就等于说:算法得到的路线长度,最多是真正最短路线的1.5倍。假设最短路线是100公里。那么算法保证:ALG≤150公里ALG\le150\text{公里}请注意,这只是质量上界,不是说算法一定会走150公里。它完全有可能得到105公里、101公里,甚至恰好100公里的最优路线。
图40-2:什么叫1.5倍近似保证?
真正最优路线(假设)100 km
Christofides 的保证上界150 km
最坏情况保证,不是实际运行里程。图中的100公里是假设的最优长度,只用于解释近似比。
这种数学保证,称为近似比(Approximation Ratio)。能够在多项式时间内找到解,同时保证解的目标值不会偏离最优值超过某个明确比例的算法,称为近似算法(Approximation Algorithm)。它与普通的启发式搜索存在重要区别。普通启发式算法可能在大量测试中表现很好,但未必拥有严格的最坏情况质量界。近似算法的价值,则在于它能够通过数学证明,为每一次符合条件的输入提供某种统一保证。这是一种不追求绝对完美,却仍然坚持数学严谨的算法设计方式。但我们马上必须面对一个问题。Christofides 算法为什么能够给出1.5倍保证?答案需要从一棵树开始。

第三幕:一条必须遵守的数学规则——三角不等式

三角不等式示意:在具有适当距离性质的空间里,从A经B到C,不会比直接从A到C更短。在进入算法细节之前,我们必须解决一个容易被忽略的问题。如果克里斯托菲德斯的算法如此优秀,为什么不能把它直接用于所有旅行商问题?答案是:它对城市之间的距离有明确要求。

经过中间城市,不能比直接去更便宜

假设有三个地点:A、B、C。如果从A直接到C的距离是10公里。而A到B是4公里,B到C是5公里。那么:4+5=9<104+5=9<10我们似乎发现了一条更短的绕行路径。可是,如果所谓的“A到C距离”已经表示两地之间最短的实际可行道路距离,那么这个数据就不合理。因为我们已经找出一条只需9公里的路线。真正的最短距离应该不超过9公里。这就是三角不等式:d(A,C)≤d(A,B)+d(B,C)\boxed{d(A,C)\le d(A,B)+d(B,C)}对于普通的平面直线距离,这条性质天然成立。而对于一个连通、道路长度非负的无向交通网络,只要每对城市之间的距离取最短可行道路长度,它也成立。但如果距离矩阵记录的是某项特殊费用、受到额外限制的服务报价,或者含有固定起步成本的运输合同,那么三角不等式不一定成立。这类数据不能未经检查就直接应用 Christofides 的1.5倍保证。此外,经典 Christofides 算法还要求距离对称:d(A,B)=d(B,A)d(A,B)=d(B,A)如果道路受到单行道限制,那么A到B的最短时间,可能不同于B到A。这就形成了另一类问题:非对称旅行商问题。

为什么三角不等式如此重要?

想象我们的路线已经经过:A→B→CA\rightarrow B\rightarrow C但之前其实已经访问过B。这时,旅行者不再需要把B作为一次新的停靠。能不能直接从A去C?如果存在三角不等式:d(A,C)≤d(A,B)+d(B,C)d(A,C)\le d(A,B)+d(B,C)那么跳过B,路线就不会变长。
图40-3:跳过重复城市,不会增加距离
ABC4 km5 km直接走不超过9 km
查看 SVG 配图原件
示意图原件 40-007-f2d40c1c8398.svg
40-007-f2d40c1c8398.svg · 点击查看大图
黄色表示经过B的两段路线,绿色表示直接从A到C。在度量距离下,直接连接不会更长。
克里斯托菲德斯正是利用这个性质,完成最后一步。他的算法先找到一条可能重复经过某些城市的封闭路线。然后,通过跳过重复顶点,逐步把它转换成每座城市只出现一次的旅行商回路。只要三角不等式成立,每一次跳过都不会增加总距离。这就是整个1.5倍证明中不可缺少的条件之一。

不是所有旅行商问题都拥有这种保证

我们必须在这里明确区分:一般 TSP: 只给出一组城市间的旅行成本,不一定满足三角不等式。度量 TSP(Metric TSP): 距离非负、对称,并满足三角不等式。欧几里得 TSP(Euclidean TSP): 城市用平面或其他欧几里得空间里的点表示,距离由直线距离计算,是度量 TSP 的一种特殊情况。Christofides 的经典1.5倍近似保证,针对的是第二类。这不是一个可以省略的小字注释。它是定理成立的重要前提。接下来,我们将在满足这些条件的世界里,开始真正构造路线。

第四幕:第一块积木——一棵尽可能便宜的树

最小生成树连接全部城市,同时避免形成回路。它不直接是一条完整旅行路线,却为最优旅行商路线提供了一个重要的成本下界。假设有七座城市。为了便于研究,我们把它们画成七个点。现在,不要急着规划一条闭合的旅行路线。先换一个问题:怎样用尽可能短的道路,把这七座城市连接起来?每座城市只要能够通过这些道路与其他城市相连即可。不要求每条路都能形成环。也不要求从某座城市出发能够不走重复道路地返回。我们只关心:使用的全部道路长度之和尽可能小。这就是**最小生成树(Minimum Spanning Tree,MST)**问题。

树为什么更容易?

在图论中,一棵包含全部 nn 个顶点的生成树,恰好有:n−1n-1条边。它必须连通。同时不能包含任何环。因此,它比一条访问全部顶点的旅行商回路少了一项要求:不必返回起点。而正是这项放松,使它可以通过成熟的多项式时间算法高效求解。例如:Prim 算法。Kruskal 算法。这些方法在图论与计算机科学中已经成为基础工具。

最小生成树与旅行商最优路线之间有什么关系?

这里有一个非常重要的结论。假设我们已经知道真正最优的旅行商路线。它经过全部城市,最后回到起点。现在,从这条封闭路线中删除任意一条边。会发生什么?原来是一条环。删去一条边以后,剩下的边仍然连接全部城市。而且不再形成回路。所以,我们得到一棵生成树。因此:这棵树的总长度不会超过原来的旅行商路线。而最小生成树,顾名思义,是全部生成树中总长度最小的一棵。所以:w(MST)≤OPT\boxed{w(MST)\le OPT}其中:w(MST)=最小生成树总权重w(MST)=\text{最小生成树总权重}OPT=真正最短旅行商路线长度OPT=\text{真正最短旅行商路线长度}这是一条很漂亮的下界关系。我们可能根本不知道最优旅行商路线长什么样。但只要算出最小生成树,就知道:真正的最优路线长度,绝不可能比这棵树更短。

既然树很便宜,为什么不能直接沿树旅行?

因为树没有回路。假设一座城市位于树的一条分支末端。旅行者沿着树走到那里之后,如果不允许使用树外的边,就必须沿原路返回。这会造成重复行走。因此,一棵生成树虽然能够连接所有城市,却不一定是一条合法的旅行商回路。怎么办?最直观的做法,就是把树上的每条边都复制一次。这样,每条原有道路都拥有两份。所有顶点的度数都会变成偶数。根据欧拉回路理论,我们就能够沿着这些边完成一条封闭的路线。接下来,再利用三角不等式跳过重复城市。这样得到的旅行商路线长度至多是:2w(MST)2w(MST)而因为:w(MST)≤OPTw(MST)\le OPT所以:ALG≤2OPT\boxed{ALG\le2OPT}这便是度量旅行商问题的一种经典2倍近似思想。

但克里斯托菲德斯不满意

如果把最小生成树上的每条边都复制一份,就意味着我们为了构造欧拉回路,额外支付了整棵树的成本。但真的有必要把所有边都复制吗?假设某个节点的度数原本就是偶数。它已经符合欧拉回路所要求的度数条件。为什么还要给它增加额外的边?这是一项明显的浪费。克里斯托菲德斯发现:真正需要修补的,不是整棵树,而只是那些度数为奇数的顶点。这项观察,打开了从2倍近似迈向1.5倍近似的大门。

第五幕:奇数度数的秘密——为什么只需要修补一半?

在图论中,顶点的度数是与该顶点相连的边数。克里斯托菲德斯利用奇度顶点的结构,决定哪些地方需要增加边。现在,让我们暂时只考虑一棵生成树。如果某个顶点连接了一条边,它的度数就是1。连接两条边,度数是2。连接三条边,度数是3。依此类推。我们把度数为1、3、5等的顶点称为奇度顶点。把度数为2、4、6等的顶点称为偶度顶点。

奇度顶点为什么一定是偶数个?

这听起来像一句绕口令。但它来自图论中一条非常基本的数学定理:握手定理(Handshaking Lemma)。假设一张无向图拥有若干条边。每条边都有两个端点。因此,如果把所有顶点的度数加起来,每条边都会被计算两次。所以:∑v∈Vdeg⁡(v)=2∣E∣\boxed{\sum_{v\in V}\deg(v)=2|E|}右边一定是偶数。而一组整数相加之后要得到偶数,其中奇数的个数就必须是偶数。因此:任何有限无向图中的奇度顶点个数都是偶数\boxed{\text{任何有限无向图中的奇度顶点个数都是偶数}}这意味着,在一棵最小生成树里,奇度顶点可能有2个、4个、6个……但不会出现恰好3个或5个奇度顶点。为什么这项性质重要?因为我们希望把所有奇度顶点两两配对。既然它们的总数一定是偶数,就能够组成完整的配对。

一次特别的匹配

假设有四个奇度顶点:A,B,C,DA,\quad B,\quad C,\quad D我们希望为它们增加两条边,使每个奇度顶点恰好额外连接一条边。这样,原本奇数的度数就会加1,变成偶数。但应该怎样配对?可以选择:(A,B),(C,D)(A,B),\quad(C,D)也可以选择:(A,C),(B,D)(A,C),\quad(B,D)或者:(A,D),(B,C)(A,D),\quad(B,C)每一种配对所需要增加的总距离,可能并不一样。所以我们需要寻找:使匹配边总长度最小的完美匹配(Minimum-Weight Perfect Matching)。这恰好与之前的匹配问题产生了联系。只不过,这里不是工人与工作之间的二分图匹配。而是在同一组奇度顶点中,寻找任意两两配对的最小总成本。
图40-4:四个奇度顶点的三种配对方式
ABCD方案一
ABCD方案二
ABCD方案三
对于四个奇度顶点,只有三种不同的完整配对方式。算法选择增加边总权重最小的一种;实际问题可以拥有更多奇度顶点。

为什么这样就能修复整棵树?

我们把最小生成树与匹配边组合起来。对于原来度数为奇数的顶点:新增一条匹配边。所以它的度数增加1,变成偶数。对于原来度数为偶数的顶点:没有新增与它相连的匹配边。所以它仍然是偶数。最终,整张组合网络中,每个顶点的度数都是偶数。并且由于最小生成树本来就连通,加入匹配边后,整个网络仍然连通。因此:组合后的多重图存在欧拉回路\boxed{\text{组合后的多重图存在欧拉回路}}这就是 Christofides 算法的第二个关键步骤。但我们还需要解释,为什么选中的匹配边不会太贵。一个非常精妙的证明,将出现在后面。现在,我们先看如何利用这张所有顶点度数为偶数的网络,构造真正的环游路线。

第六幕:从欧拉回路到旅行商回路——最后一次神奇的跳跃

欧拉于1736年研究柯尼斯堡七桥问题,开创了图论早期的重要研究方向。欧拉回路与旅行商要求的哈密顿回路并不相同。现在,我们已经拥有一张连通的网络。它包含一棵最小生成树。还包含用于修补奇度顶点的匹配边。所有顶点的度数都是偶数。接下来,我们需要使用一位更早的数学家留下的成果。他就是十八世纪的莱昂哈德·欧拉(Leonhard Euler)。

一条线路,恰好走过每条边一次

1736年,欧拉研究了柯尼斯堡七桥问题。他希望知道,一个人是否能够在只经过每座桥一次的条件下,走遍全部七座桥。最终,他将问题从实际地理结构抽象为点与边之间的关系。由此开启了图论研究中的一条重要道路。在今天,我们知道:对于一张连通的无向图,如果每个顶点的度数都是偶数,那么就存在一条封闭的路线,能够恰好经过每条边一次。这叫作欧拉回路(Eulerian Circuit)。现在回头看我们的最小生成树与匹配边。每个顶点的度数都已经变成偶数。因此,它一定存在欧拉回路。这不是猜测。而是由图论定理严格保证的结论。

但是,欧拉回路不是旅行商回路

这是整章最容易混淆的两个概念。欧拉回路要求:每条边恰好经过一次。但是允许某个顶点被多次访问。哈密顿回路要求:每个顶点恰好作为一次正式访问点,最终返回起点。两者的重点完全不同。
图40-5:欧拉回路与哈密顿回路
ABCD欧拉回路关注每条边的使用,允许顶点重复出现
ABCD哈密顿回路关注每个城市恰好访问一次
概念示意,左侧强调允许顶点重复、右侧强调只保留第一次访问。实际 Christofides 算法在多重图上构造欧拉回路,随后通过捷径化得到哈密顿回路。

跳过所有已经访问过的城市

假设我们找到的欧拉回路是:A→B→C→B→D→E→AA\rightarrow B\rightarrow C\rightarrow B\rightarrow D\rightarrow E\rightarrow A这里的B被访问了两次。但旅行商并不需要第二次把B当成一个新的停靠点。因此,我们可以将:C→B→DC\rightarrow B\rightarrow D替换为:C→DC\rightarrow D得到:A→B→C→D→E→AA\rightarrow B\rightarrow C\rightarrow D\rightarrow E\rightarrow A这就是捷径化(Shortcutting)。如果满足三角不等式:d(C,D)≤d(C,B)+d(B,D)d(C,D)\le d(C,B)+d(B,D)那么,跳过B不可能让整条路线更长。对于其他重复顶点,我们可以使用同样的方法。最终,便能得到一条访问每座城市恰好一次、并回到起点的哈密顿回路。

为什么不能直接把所有重复节点删掉?

这里还隐藏着一个实现细节。我们不能只把欧拉回路中的重复文字删除,然后不考虑新连接。例如:A→B→C→B→DA\rightarrow B\rightarrow C\rightarrow B\rightarrow D删去第二个B之后,必须新建从C到D的连接。它的长度应该使用:d(C,D)d(C,D)而不是继续沿用原来两段路线的长度。如果图中没有直接的C到D边,就需要模型本身提供相应的度量距离,例如道路网络里的最短路距离。因此,捷径化的正确性,实际上依赖我们在第三幕强调的完整距离模型。这也是为什么数学定理的前提如此重要。如果没有三角不等式,就不能保证这种跳过操作不会使总成本增加。

四块积木终于组合完毕

到这里,Christofides 算法已经全部出现。
图40-6:Christofides 算法的完整计算流程
1
最小生成树以最低总边权连接全部城市

2
寻找奇度顶点记录生成树中度数为奇数的城市

3
最小权完美匹配为奇度顶点增加总成本尽可能小的配对边

4
构造欧拉回路每个顶点度数为偶数,因此能够经过每条边一次并返回

5
捷径化跳过重复城市,形成哈密顿回路
克里斯托菲德斯的伟大之处,不在于他从无到有地发明了上述全部数学工具。最小生成树早已有成熟研究。匹配问题已经拥有自己的算法理论。欧拉回路更是十八世纪以来的经典图论概念。真正的突破,在于他发现了这些工具之间能够互相配合的结构。最小生成树提供一个便宜的骨架。最小权匹配负责修补奇数度数。欧拉回路保证封闭遍历存在。三角不等式保证跳过重复城市不会变贵。不同年代的数学成果,在1976年组合成了一种新的近似算法。但现在还剩下最后一个问题。为什么最终路线的长度,恰好能够限制在最优长度的1.5倍以内?这需要一份真正的数学证明。

第七幕:1.5倍从哪里来?一份可以逐行检查的证明

Christofides 的近似比证明将最终路线拆解为两项成本:最小生成树成本与最小权匹配成本。关键在于分别给出它们相对于最优路线的上界。我们定义四个数学对象:OPT=最短旅行商回路的长度OPT=\text{最短旅行商回路的长度}T=最小生成树T=\text{最小生成树}M=奇度顶点上的最小权完美匹配M=\text{奇度顶点上的最小权完美匹配}C=最终输出的旅行商回路C=\text{最终输出的旅行商回路}我们希望证明:w(C)≤32OPT\boxed{w(C)\le\frac32OPT}第一部分已经解决。因为从最优旅行商回路中删去一条边,可以得到一棵生成树,所以:w(T)≤OPT\boxed{w(T)\le OPT}关键是第二部分。我们需要证明:w(M)≤12OPT\boxed{w(M)\le\frac12OPT}为什么匹配成本不会超过最优路线长度的一半?

第一小步:只保留奇度顶点

设生成树中度数为奇数的顶点集合为:O={v1,v2,…,v2k}O=\{v_1,v_2,\ldots,v_{2k}\}握手定理告诉我们,奇度顶点的数量一定是偶数。假设我们已经知道真正的最优旅行商回路。沿着这条回路行进,把不属于集合 OO 的城市暂时跳过。因为距离满足三角不等式,得到的这条只经过奇度顶点的环游路线,其长度不会超过原来的最优路线。所以:w(奇度顶点环游路线)≤OPTw(\text{奇度顶点环游路线})\le OPT

第二小步:把一条偶数顶点环分成两种匹配

现在,我们拥有一条包含偶数个顶点的环:v1→v2→⋯→v2k→v1v_1\rightarrow v_2\rightarrow\cdots\rightarrow v_{2k}\rightarrow v_1把沿途的边交替涂成两种颜色。第一组:(v1,v2),(v3,v4),…(v_1,v_2),(v_3,v_4),\ldots第二组:(v2,v3),(v4,v5),…,(v2k,v1)(v_2,v_3),(v_4,v_5),\ldots,(v_{2k},v_1)每一种颜色,都恰好将所有奇度顶点两两配对一次。因此,它们都是合法的完美匹配。
图40-7:一条环,可以拆成两份完美匹配123456
第一组匹配
第二组匹配
六个奇度顶点构成一条环时,隔边选取可以得到两份完美匹配。两份匹配的总边权之和恰好等于该环的长度。
设两组匹配分别为:M1,M2M_1,\quad M_2它们的总成本之和,就是整个环的长度:w(M1)+w(M2)≤OPTw(M_1)+w(M_2)\le OPT那么,两组之中成本较低的那一组,必定满足:min⁡(w(M1),w(M2))≤12OPT\min(w(M_1),w(M_2))\le\frac12OPT而我们通过算法选择的 MM,是所有合法完美匹配中成本最小的一组。它当然不会比刚才两组中的较便宜者更贵。所以:w(M)≤12OPT\boxed{w(M)\le\frac12OPT}证明完成。

第三小步:树与匹配的成本相加

组合图包含生成树与新增匹配边。将重复边视为不同的边副本,组合图的总边权为:w(T)+w(M)w(T)+w(M)我们已经分别得到:w(T)≤OPTw(T)\le OPT以及:w(M)≤12OPTw(M)\le\frac12OPT因此:w(T)+w(M)≤OPT+12OPTw(T)+w(M) \le OPT+\frac12OPT于是:w(T)+w(M)≤32OPT\boxed{w(T)+w(M)\le\frac32OPT}

最后一步:捷径化不会增加成本

组合图存在欧拉回路。它的总长度正好是组合图所有边权之和:w(Euler)=w(T)+w(M)w(Euler)=w(T)+w(M)再通过捷径化跳过重复城市。由于三角不等式成立:w(C)≤w(Euler)w(C)\le w(Euler)把所有关系连起来:w(C)≤w(T)+w(M)≤OPT+12OPT=32OPT\begin{aligned} w(C) &\le w(T)+w(M)\\ &\le OPT+\frac12OPT\\ &=\frac32OPT \end{aligned}终于得到:w(C)OPT≤1.5\boxed{\frac{w(C)}{OPT}\le1.5}这就是 Christofides 算法的近似比保证。[Springer Nature Link][剑桥大学计算机科学与技术系]

为什么这项证明尤其漂亮?

整段证明中,我们完全不需要提前求出真正的最短旅行商路线。我们只是借助最优路线这个数学对象,推导出两项成本上界。第一项来自最小生成树。第二项来自奇度顶点的最小权匹配。最后,再利用捷径化的性质,将它们组合起来。于是,算法能够在不知道最优答案的情况下,保证自己与最优答案之间的距离。这是一种非常成熟的算法设计思想。不需要先获得完美,才能对不完美的质量作出严格保证。

第八幕:互动实验室——七座城市,五步找到一条有保证的路线

旅行商问题的计算实验,通常先将城市简化为平面上的点,再利用距离矩阵比较不同路线。下面使用自造坐标,不对应真实公路位置。前面讲了这么多数学结构,现在轮到我们亲手操作。我们将七座虚构城市放在一张平面地图上。每两座城市之间的距离,定义为它们之间的欧几里得直线距离。因此,这个实验天然满足对称性和三角不等式。你可以选择不同的城市布局。然后逐步查看:原始城市分布。最小生成树。奇度顶点与匹配边。欧拉回路。最终的 Christofides 环游路线。为了能够验证结果,实验室还会使用穷举方法计算这些小型案例的真正最优路线。这样,你就能直接比较:Christofides 得到的路线,与真正的最短路线,究竟相差多少?
图40-8:Christofides 算法实验室修改布局并推进步骤;算法将重新生成最小生成树、匹配和最终路线。
0 / 4
准备阶段:城市分布目前只显示城市坐标。算法将根据各城市之间的直线距离计算路线。
ABCDEFG
生成树
匹配 / 欧拉回路
最终环游路线
最小生成树长度

176.15

奇度顶点匹配长度

92.81

Christofides 路线

247.75

穷举得到的真正最优

229.38

当前路线 / 最优路线

1.080 倍

理论最小值 1.0理论上界 1.5
本例的路线比真正最优路线长约 8.0%。这个数值是当前布局的实际结果,不是算法在所有输入中的固定表现。
本实验为7座或6座虚构城市;地图距离单位任意,不代表真实公里数。最小权匹配与精确最优路线均使用小规模穷举验证;大型实例必须改用高效的匹配算法。

请重点观察三个现象

第一个现象:最小生成树的总长度,总是不超过真正的最短旅行商回路。但它本身不是一条合法的闭合旅行路线。第二个现象:加入最小权完美匹配之后,生成树的奇度顶点被修复。新网络的总边权增加了,但它变成了可以完成欧拉回路的结构。第三个现象:从欧拉回路中跳过重复城市之后,路线长度不会增加。你还可以切换不同的城市布局,观察 Christofides 有时非常接近最优解,有时却会产生明显的额外路程。这才是近似算法真正的含义。它没有保证每次都得到最短路线。但它保证最坏情况下,输出路线与最优路线之间仍然存在一项可以证明的比例界限。

一个需要避免的误解

实验中为了验证小规模问题,我们使用了枚举方法计算最优路线。但这并不是 Christofides 算法日常运行所需要的一步。对于真实的大规模问题,我们通常根本不知道精确的最优路线。Christofides 的1.5倍保证,不依赖程序真的算出这个最优答案。本实验计算最优解,是为了让读者看清近似算法实际产生了多少误差。

第九幕:真正运行算法——把1976年的思想写进现代程序

现代图算法库已经将最小生成树、最小权匹配和欧拉回路等功能整理为可复用的程序模块。这使经典近似算法可以直接用于教学与工程原型。在前面的实验里,我们已经亲手走过了五个步骤。现在,我们将它们写成一份真正可以运行的 Python 程序。这份程序使用 NetworkX。它不是从零重新发明图论算法,而是借助已经经过研究与实现的图算法工具,将 Christofides 的五个步骤组合起来。这与原始研究的精神非常一致。克里斯托菲德斯最重要的发现,就是如何把不同的图论工具组合成一项具有严格性能保证的算法。

第一步:建立七座城市及其距离矩阵

为了与交互实验保持一致,我们使用相同的七个坐标。
python
cities = {
    "A": (14, 36),
    "B": (21, 79),
    "C": (33, 21),
    "D": (55, 83),
    "E": (92, 82),
    "F": (37, 41),
    "G": (75, 61),
}
我们会使用欧几里得距离计算城市之间的成本。从而保证距离满足算法所需要的数学性质。

第二步:完整实现

python

import math
import itertools
import networkx as nx


cities = {
    "A": (14, 36),
    "B": (21, 79),
    "C": (33, 21),
    "D": (55, 83),
    "E": (92, 82),
    "F": (37, 41),
    "G": (75, 61),
}


def distance(a, b):
    x1, y1 = cities[a]
    x2, y2 = cities[b]

    return math.hypot(x1 - x2, y1 - y2)


def route_length(route):
    return sum(
        distance(route[i], route[i + 1])
        for i in range(len(route) - 1)
    )


# 构造完整的无向度量图
G = nx.Graph()
G.add_nodes_from(cities)

for a, b in itertools.combinations(cities, 2):
    G.add_edge(a, b, weight=distance(a, b))


# 1. 求最小生成树
tree = nx.minimum_spanning_tree(
    G, weight="weight"
)

tree_cost = tree.size(weight="weight")


# 2. 找出生成树里的奇度顶点
odd_vertices = [
    v for v, degree in tree.degree()
    if degree % 2 == 1
]


# 3. 在奇度顶点之间求最小权完美匹配
odd_graph = G.subgraph(odd_vertices).copy()

matching = nx.min_weight_matching(
    odd_graph,
    weight="weight"
)

matching_cost = sum(
    G[u][v]["weight"]
    for u, v in matching
)


# 4. 组合为允许重复边的多重图
multi = nx.MultiGraph(tree)

for u, v in matching:
    multi.add_edge(
        u, v,
        weight=G[u][v]["weight"]
    )

assert nx.is_eulerian(multi)


# 5. 求欧拉回路
start = next(iter(cities))

euler_walk = [start]

for u, v in nx.eulerian_circuit(
    multi, source=start
):
    euler_walk.append(v)


# 6. 跳过重复城市
visited = set()
tour = []

for city in euler_walk:
    if city not in visited:
        visited.add(city)
        tour.append(city)

tour.append(tour[0])

approx_cost = route_length(tour)


# 验证质量保证
print("最小生成树:", round(tree_cost, 2))
print("匹配成本:", round(matching_cost, 2))

print("欧拉回路:")
print(" -> ".join(euler_walk))

print("Christofides路线:")
print(" -> ".join(tour))

print("路线长度:", round(approx_cost, 2))

assert approx_cost <= (
    tree_cost + matching_cost + 1e-9
)
你可以仔细观察程序中的三段代码。第一段:
python
tree = nx.minimum_spanning_tree(G)
负责得到最小生成树。第二段:
python
matching = nx.min_weight_matching(odd_graph)
负责修补所有奇度顶点。第三段:
python
nx.eulerian_circuit(multi)
负责构造欧拉回路。这三项看似独立的操作,最终共同组成了 Christofides 算法。需要说明,MultiGraph 是一个多重图。如果最小生成树已经包含某条边,而匹配又选中了相同两个端点,算法必须允许这条边出现两次。不能简单地把它们当成同一条边,否则可能破坏欧拉回路需要的度数结构。

第三步:验证真实最优答案

对于七座城市,我们还可以使用穷举作为教学验证。
python

from itertools import permutations


def brute_force_tsp():
    start = "A"

    others = [
        city for city in cities
        if city != start
    ]

    best_route = None
    best_cost = float("inf")

    for order in permutations(others):
        candidate = [
            start,
            *order,
            start
        ]

        cost = route_length(candidate)

        if cost < best_cost:
            best_cost = cost
            best_route = candidate

    return best_route, best_cost


optimal_tour, optimal_cost = brute_force_tsp()

print("真实最优路线:")
print(" -> ".join(optimal_tour))

print("真实最优长度:", round(optimal_cost, 2))

print(
    "当前路线与最优路线之比:",
    round(approx_cost / optimal_cost, 4)
)

assert approx_cost <= 1.5 * optimal_cost + 1e-9
对于这个规模,穷举只需要检查:6!=7206!=720种固定起点的访问顺序。计算量很小。但如果把城市数量扩展到几十座,穷举就不再适合作为普通的求解策略。

NetworkX 里甚至已经有现成的 Christofides 算法

如果你的目标只是直接求一条近似路线,而不是教学研究,那么 NetworkX 已经提供了对应接口。
python

import networkx as nx

route = nx.approximation.christofides(
    G,
    weight="weight"
)

length = route_length(route)

print("路线:", " -> ".join(route))
print("长度:", round(length, 2))
NetworkX 的官方文档将它描述为完整无向加权图上的3/2近似算法,并明确引用 Christofides 1976年的研究报告。[NetworkX 3.7 documentation][NetworkX 3.7 documentation]不同实现可能因为最小生成树中的同权选择、匹配的等价解以及欧拉回路遍历顺序不同,输出不同的合法路线。这些路线不一定具有相同长度。但只要算法正确实现,输入满足规定的度量条件,它们都受到相同的数学上界约束。

理论上的多项式时间,与教学穷举不同

这里必须做一个非常重要的区分。在交互实验中,为了直观理解,我们对少量奇度顶点的匹配进行了穷举。这适合七座城市的教学模型。但如果有数百个奇度顶点,穷举全部两两配对并不高效。真正的多项式时间 Christofides 算法,需要使用适当的最小权完美匹配算法,例如基于 Edmonds 花算法及其后续改进的相关方法。在原始论文中,克里斯托菲德斯指出,利用当时已知的匹配算法,可以实现:O(n3)O(n^3)量级的总时间复杂度。今天不同的实现可能采用其他数据结构和算法,其具体复杂度需要结合所用匹配子程序分析。因此:Christofides 的多项式时间保证,依赖高效求解最小权完美匹配,而不是把全部配对方式逐一列出来。这也是它与普通穷举法的根本区别之一。

第十幕:另一位研究者、四十多年的等待,以及2020年的突破

1970年代的算法研究界,计算复杂性和近似算法逐渐成为重要研究方向。同一种数学思想,有时也会在不同国家独立出现。克里斯托菲德斯的1976年报告,在后来的算法教材中变得非常著名。但完整的历史,还有另一位研究者。他的名字是阿纳托利·伊万诺维奇·谢尔久科夫(Anatoliy Ivanovich Serdyukov)。

1978年,苏联出现了独立研究

1978年,谢尔久科夫发表了一篇俄语论文。其中包含与 Christofides 方法本质上相同的3/2近似算法思想。从时间上看,克里斯托菲德斯的研究报告发表于1976年。谢尔久科夫的相关论文发表于1978年。数学史研究通常将两项成果视为独立发现。因此,部分现代文献使用:Christofides–Serdyukov 算法这一名称。2020年,René van Bevern 与 Viktoriia A. Slugina 在数学史期刊《Historia Mathematica》发表专门研究:A Historical Note on the 3/2-Approximation Algorithm for the Metric Traveling Salesman Problem。文章梳理了谢尔久科夫研究的历史背景,并提供其俄语论文的英文翻译。[ScienceDirect][BibBase]这段经历,与第38章匈牙利算法的历史产生了有趣的呼应。有些算法曾在不同国家独立出现。有些成果因为语言、学术交流条件或发表渠道,无法立即为整个国际研究群体所熟悉。历史研究的作用,就是逐渐恢复这些被忽略的贡献。

1976年的报告,直到2022年才以期刊论文重新发表

克里斯托菲德斯1976年研究报告的历史资料参考。该成果后来于2022年在《Operations Research Forum》重新以期刊论文形式发表。这里还有一项容易被误解的出版史细节。Christofides 算法来自1976年的研究报告。但如果你在学术网站上查找同名论文,可能会看到一个让人困惑的日期:2022年。这是因为《Operations Research Forum》于2022年重新发表了这项经典研究。这并不意味着算法是在2022年才被发明。它在1976年就已经出现,并被学界广泛引用。重新发表的价值,是让这份具有历史意义的研究能够更容易被现代读者查阅。[Springer Nature Link][Springer Nature Link]对于理解科学史来说,这种区分非常重要。研究形成的日期。技术报告的日期。会议报告的日期。正式期刊重新发表的日期。它们有时并不相同。不能简单地把数据库页面上最醒目的出版年份,当作一项算法真正诞生的时间。

为什么1.5倍保证如此难以打破?

克里斯托菲德斯的方法之所以经典,不只是因为它容易解释。更因为它在相当长的时间里,成为一般度量旅行商问题近似保证的重要基准。它使用简单而可靠的数学结构,得到:ALG≤1.5OPTALG\le1.5OPT研究人员尝试了各种改进。改进最小生成树的选择。优化奇度顶点匹配。采用更复杂的随机化与线性规划技术。但要在全部度量 TSP 实例上,严格证明一个统一优于1.5的近似比,并不容易。这里必须区分两种情况。在实际测试中,有许多算法可以经常找到比 Christofides 更短的路线。但这不代表它们一定拥有更强的通用最坏情况近似保证。找到实际表现优秀的启发式算法,与证明一个更好的全局近似比,是两种不同的研究任务。

2020年,一项极其微小却重要的突破

2020年,华盛顿大学的三位研究人员:Anna R. Karlin、Nathan Klein、Shayan Oveis Gharan,公布了一项新研究。他们证明,对于一般度量 TSP,可以设计出一项随机化多项式时间算法,使其输出路线的期望长度满足:E[ALG]≤(32−ε)OPT\boxed{\mathbb E[ALG]\le \left(\frac32-\varepsilon\right)OPT}其中:ε>10−36\varepsilon>10^{-36}这项结果在2021年 STOC 会议上发表,2023年5月18日由《Operations Research》在线发表,收入2024年的正式卷期。[Operations Research][arXiv]乍看之下,这个改进小得惊人。10−3610^{-36}是一个小数点后有许多个零的数。它不会让普通配送车辆突然减少大量行驶距离。但从理论上看,它证明了一件此前长期没有得到证明的事情:Christofides 的1.5倍界限,并不是一般度量旅行商问题近似算法无法突破的数学极限。需要注意两点。第一,这项结果是具有期望性能保证的随机化算法,而不是简单地让 Christofides 的每一条输出路线都缩短固定比例。第二,对于一些特殊的旅行商问题,例如固定维度的欧几里得 TSP,研究者早已有能够达到任意固定 1+ε1+\varepsilon 近似比例的多项式时间近似方案。2020年的突破,针对的是更加一般的度量 TSP,不能与这些特殊问题的结果混淆。

一个小小的比例,也可能代表漫长的数学探索

这件事其实与整个《算法的故事》系列的主题十分一致。数学进步,不总意味着某个数字突然提高一百倍。有时候,证明某个原本不清楚能否突破的界限,哪怕只前进一小步,也需要完全不同的理论工具。克里斯托菲德斯的1.5倍算法,依靠的是生成树、匹配与欧拉回路。后来的突破,则需要研究更加复杂的概率分布、随机生成树和组合结构。这些研究并没有使1976年的经典方法失去价值。反而让我们更加清楚地看到,Christofides 的组合思路为什么如此深刻。

第十一幕:真实世界中的路线规划,远比一条环复杂

现代物流中的车辆路径规划往往需要考虑多辆车、不同装载能力、送货时间窗和驾驶限制。经典旅行商问题是其中的一项重要数学基础,但不是完整的物流调度模型。现在,我们回到真实世界。假设一家物流公司希望给配送车辆安排路线。有一座仓库。有几十个送货地点。车辆从仓库出发,完成配送之后返回。这看起来就是旅行商问题。但如果真正进入物流系统,你很快会发现:现实比数学课本更加复杂。

第一项限制:不止一辆车

如果公司有十辆车,那么送货任务应该怎样分配?哪些地点交给第一辆?哪些地点交给第二辆?每辆车又应该按照什么顺序访问?这不再是一名旅行商的单条回路问题。它进入了**车辆路径问题(Vehicle Routing Problem,VRP)**的研究领域。

第二项限制:车辆容量

假设一辆货车最多装载5吨货物。某些客户需要1吨。某些客户需要2吨。某些客户需要500公斤。即使一条路线距离很短,只要沿途配送总量超过车辆能力,也不能执行。因此,我们需要考虑容量约束。

第三项限制:时间窗

某个客户只在上午九点到十一点之间收货。另一个客户要求下午两点之前送达。道路还可能出现拥堵。装卸货也需要时间。这时,路线的访问顺序不仅影响距离,还会影响配送能否按时完成。

第四项限制:距离不一定对称

在真实城市里,单行道、限行规则和不同方向的交通状态,可能使:d(A,B)≠d(B,A)d(A,B)\ne d(B,A)此时不能直接套用经典 Christofides 的1.5倍定理。如果我们通过道路网络的最短路径计算一对地点之间的距离,虽然通常仍然可以获得某种有向三角不等式,但它不再保证经典算法所要求的对称性。这类问题需要采用与非对称或其他约束相适应的方法。

第五项限制:路线可能需要随时调整

现实配送计划并非永远静止。客户可能取消订单。司机可能临时需要休息。道路可能封闭。新的任务可能在配送过程中出现。因此,现代系统有时需要不断重新优化路线。而不是在清晨计算出一个路线之后,就要求所有车辆整天严格按照它执行。这说明:一种有严格近似保证的算法,可以是复杂系统的重要基础,却不必然是整个现实系统的完整解决方案。

精确算法、近似算法和启发式算法应该怎样选择?

对于不同的实际任务,三类算法都拥有自己的价值。
方法类型主要目标适合情境
精确算法证明得到的路线是最短的规模允许、必须验证最优性
近似算法快速得到带数学质量保证的方案需要通用的最坏情况性能界
启发式与局部搜索在可接受时间内寻找高质量路线大规模实际优化、追求经验效果
这不是一个严格互斥的分类。现代优化系统经常把它们组合使用。例如,可以先利用 Christofides 产生一条质量有保证的路线。再使用2-opt或其他局部搜索技术,尝试通过交换若干条边进一步缩短它。如果每次局部改动都只在确实改善路线时接受,那么经过改进的合法路线,不会比原来的 Christofides 路线更长。因此,原来的1.5倍保证也不会被这种单调改善破坏。但这不意味着经过局部搜索之后,算法自动拥有一个更好的统一最坏情况近似比。实际效果改善,与理论保证增强,是两件不同的事情。

一个值得所有软件工程师记住的问题

当我们准备把算法放进真实系统时,应该先问:我们究竟需要什么?是一定要找到数学上的最优解?是需要一个明确的最坏情况质量保证?还是只需要在特定硬件上、规定时间之内,求得足够好的方案?如果必须在100毫秒内完成一次决策,那么一个需要数小时才能证明最优的算法,可能并不适合。反过来,如果某项计划涉及巨大的长期投资,优化结果每改善1%就意味着数百万成本,那么花费更多时间获得可靠的最优性证明,也可能完全值得。算法的价值,从来不只是运行速度或者数学形式的美丽。它还在于能否满足实际任务所需要的可靠性、成本与质量要求。而 Christofides 算法所开创的近似设计思想,正是在这些需求之间提供了另一种选择。

尾声:不完美,也可以拥有严格的保证

让我们再次回到1976年。克里斯托菲德斯正在研究旅行商问题。在他的研究之前,数学家已经能够利用最小生成树,构造拥有2倍近似保证的旅行路线。这当然是一项成果。但是,他注意到一种浪费。如果我们希望从生成树获得欧拉回路,为什么一定要把每条边都复制一遍?真正妨碍欧拉回路存在的,不是整棵树。而是那些度数为奇数的顶点。如果只修补它们呢?于是,最小权完美匹配进入了算法。生成树连接全部城市。匹配修复奇度结构。欧拉回路提供封闭遍历。三角不等式允许跳过重复城市。这四种看似分散的数学思想,突然形成了一条完整的计算道路。更重要的是,克里斯托菲德斯没有停留在提出一个看起来不错的方法。他证明了这个方法的质量。他证明:生成树的成本不超过最优路线。奇度顶点匹配的成本不超过最优路线的一半。而最终的捷径化,也不会使路线更长。于是:ALG≤1.5OPT\boxed{ALG\le1.5OPT}这项公式的意义,甚至超过了旅行商问题本身。因为它改变了我们对算法成功的理解。在许多传统算法问题中,人们希望得到精确答案。两个整数的最大公约数是多少?一个数字究竟是不是素数?某张网络里的最大流量是多少?这些问题,都能够在适当条件下获得严格的数学答案。但还有许多组合优化问题。它们的可能性数量增长得太快。尽管可以构造精确算法,却不一定能够在我们拥有的计算资源下,及时得到最优解。这时候,人类面临一个选择。是因为找不到绝对最优,就拒绝接受任何答案?还是寻找一种能够在有限时间内产生良好方案,同时又具备严格质量保证的计算方法?克里斯托菲德斯选择了后一条道路。但他并没有放弃严谨。恰恰相反。他把严谨从“保证答案绝对最优”,扩展到了“严格保证答案不会偏离最优太远”。这是算法设计的一项深刻转变。算法并不一定要消除全部不确定性。也不一定要处理全部可能的组合。它可以承认自身的能力存在边界。然后,用数学证明这个边界究竟在哪里。几十年之后,研究人员又进一步突破了1.5倍的理论界限。尽管改进十分微小,但它展示了另一件事:即使是已经成为经典的近似保证,也可能通过新的数学思想继续改进。科学的探索没有真正结束。一个看起来已经足够优秀的算法,也可能成为后来研究者继续前进的起点。

第二篇的最后一个问题

回顾本篇,我们已经走过五种不同的优化思想。
《寻找世界的最优解》· 五章回顾
第36章单纯形法在资源约束中寻找最优生产方案
第37章最大流最小割从网络容量与瓶颈结构中证明最大输送量
第38章匈牙利算法找到整体成本最低的任务分配
第39章延迟接受算法让拥有独立偏好的参与者形成稳定匹配
第40章Christofides 近似算法在无法轻易得到精确最优解时,给出严格的质量保证
这五章其实都在回答同一个问题。当选择如此之多,以至于人类无法凭直觉处理时,算法应该怎样帮助我们?丹齐格告诉我们,可以通过数学约束寻找最优。福特与富尔克森告诉我们,网络的结构隐藏着最优性的证据。库恩告诉我们,局部最便宜的选择未必形成整体最优。盖尔与沙普利告诉我们,成本最优的分配不一定稳定。克里斯托菲德斯则告诉我们,当严格最优难以高效获得时,仍然可以认真研究答案的质量界限。这五种思想,共同构成了现代运筹学和组合优化的重要基础。但它们还揭示了一项更深刻的原则。最好的算法,不一定永远给出完美答案;它必须能够清楚说明自己解决了什么问题、遵守了什么条件,以及能够为结果提供怎样的保证。当一个算法能够诚实地解释自己的能力边界时,它就获得了另一种可靠性。而这份可靠性,往往比“看起来总是很聪明”更加重要。

历史档案:事实依据与文学重构

本章特别核查了原始研究报告、1976年会议档案,以及后来对独立发现和理论改进的研究。
1976年 · 克里斯托菲德斯原始研究Nicos Christofides — Worst-Case Analysis of a New Heuristic for the Travelling Salesman Problem1976年形成的经典研究,2022年重新发表于《Operations Research Forum》。完整呈现最小生成树、奇度顶点匹配、欧拉回路与1.5倍近似界限的证明。

1976年 · 卡内基梅隆大学会议档案Symposium on New Directions and Recent Results in Algorithms and Complexity会议于1976年4月7—9日举行。档案第47页(PDF第47页,零起始第46页)保存了 Christofides 研究摘要,会议日程亦列出了相应报告。

人物生平 · 帝国理工学院官方纪念文章Obituary: Nicos Christofides (1942–2019)核查克里斯托菲德斯的教育、工程研究、运筹学工作,以及家人关于在餐桌上整理英国公路地图的回忆。

1954年 · 49城市旅行商问题Dantzig、Fulkerson、Johnson — Solution of a Large-Scale Traveling-Salesman Problem用于核查早期精确求解旅行商问题的历史,以及线性规划与割平面技术的贡献。

2020年 · 独立发现的历史考证van Bevern & Slugina — A Historical Note on the 3/2-Approximation Algorithm研究 Serdyukov 1978年独立发表的成果,并提供相关俄语论文的英文翻译。

2020—2024年 · 理论界限的新进展Karlin、Klein、Oveis Gharan — A (Slightly) Improved Approximation Algorithm for Metric TSP核查随机化算法在一般度量 TSP 中严格突破1.5倍期望近似界的结果及发表时间。
本章中,克里斯托菲德斯的生平、1976年会议与研究报告、1954年的49城市成果、1978年谢尔久科夫的独立研究,以及2020年之后的理论改进,均有历史文献支持。开篇的旅行者场景以及算法形成过程中所用的叙事转折属于教学性的文学组织,不代表存在完整记录的研究者原话。七座城市的坐标、互动实验、数学图解与 Python 代码均为现代教学设计。所有近似比结论均限定于相应数学前提之下,不将其推广为任意现实交通路线的无条件保证。
第二季 · 第二篇完结

下一篇:让机器理解空间

第41—45章,将从资源优化和抽象网络,转向几何世界、空间划分、路径规划与机器人运动。
下一章预告 · 第41章

《用一根橡皮筋包住世界:凸包算法的发现》

1972年,一位数学家开始研究一个看似简单的几何问题。假设在平面上随机撒下一百颗钉子。如果拿一根橡皮筋,将这些钉子全部套住,然后慢慢松开,橡皮筋最终会形成什么形状?它不会经过所有内部的钉子。而是紧紧包住最外围的那些点。这个形状,叫作凸包(Convex Hull)。但计算机没有真正的橡皮筋。它只有坐标、比较和数值运算。那么,怎样让计算机只通过计算,判断哪些点应该位于最外围?下一章,我们将认识 Ronald Graham,追踪凸包算法的发展,并通过向量叉积、排序和栈结构,一步步构造著名的 Graham Scan。从一根想象中的橡皮筋开始,进入计算几何的世界。
——《算法的故事》第二季 · 第40章 完