《算法设计与分析》系统地介绍了算法设计与分析的概念和方法,共4篇内容。第1篇介绍算法设计与分析的基本概念,结合穷举法、排序问题及其他一些算法,对算法的时间复杂性的概念及复杂性的分析方法作了较为详细的叙述;第2篇以算法设计技术为纲,从合并排序、堆排序、离散集合的union和find操作开始,进而介绍递归技术、分治法、贪婪法、动态规划、回溯法、分支与限界法和随机算法等算法设计技术及其复杂性分析;第3篇介绍计算机应用领域里的一些算法,如图和网络流,以及计算几何中的一些问题;第4篇介绍算法设计与分析中的一些理论问题,如NP完全问题、计算复杂性问题、下界理论问题,最后介绍近似算法及其性能分析。
《算法设计与分析》内容选材适当、编排合理、由浅入深、循序渐进、互相衔接、逐步展开,并附有大量实例,既注重算法的思想方法、推导过程和正确性的证明技术,也注重算法所涉及的数据结构、算法的具体实现和算法的工作过程。
《算法设计与分析》可作为高等院校计算机专业本科生和研究生的教材,也可作为计算机科学与应用的科学技术人员的参考资料。
《算法设计与分析》内容选材适当、编排合理、逐步展开,是高等院校计算机专业本科生和研究生必选的教材。
前 言
计算机系统中的任何软件,都是按特定的算法来予以实现的。算法性能的好坏,直接决定了所实现软件性能的优劣。如何判定一个算法的性能?用什么方法来设计算法?所设计的算法需要多少运行时间、多少存储空间?在实现一个软件时,这些都是必须予以解决的问题。计算机中的操作系统、语言编译系统、数据库管理系统,以及各种各样的计算机应用系统中的软件,都离不开用具体的算法来实现。因此,算法设计与分析是计算机科学与技术的一个核心问题,也是大学计算机专业本科生及研究生必修的一门重要的专业基础课程。通过算法设计与分析这门课程的学习,读者能够掌握算法设计与分析的方法,并利用这些方法去解决在计算机科学与技术中所遇到的各种问题,设计计算机系统的各种软件中所可能遇到的算法,并对所设计的算法做出科学的评价。因此,算法设计与分析,不仅对计算机专业的科学技术人员,而且对使用计算机的其他专业技术人员,都是非常重要的。
本书内容选材适当、编排合理、由浅入深、循序渐进、互相衔接、逐步展开,在编写过程中,尽可能遵循下面几个原则。
(1)面对学生,尽可能用通俗的语言来表达深奥的问题。因此,公式推导尽可能详尽,因为这样才不会为难学生;所用到的专门术语或知识来龙去脉尽可能介绍清楚,因为这样,学生才不会感到错愕和不知所措;对问题的叙述,尽可能开门见山,使学生能较快地、容易地接触到问题的实质。
(2)实现算法的思想方法和推导过程尽可能详细和易于理解,因为这样,学生才能深刻地理解和掌握算法的工作原理。
(3)对算法的某些理论基础和定理的证明给予足够的重视,定义的叙述尽可能严谨,方法推导、定理证明的逻辑尽可能严密,因为这可以培养学生良好的逻辑思维能力和严谨规范的科学方法,而设计并实现一个算法,具有良好的逻辑思维能力和严谨规范的科学方法是很重要的。
(4)算法具体实现的描述、所涉及的数据结构和变量,都做出较为详尽的说明。因为有些学生尽管知道了思想方法,也了解了实现步骤,但具体实现起来,有时却觉得束手无策。对算法的具体实现和所用到的数据结构的较为详细的描述,可以培养学生的具体实践能力,使学生学会如何使用所学过的知识来设计和实现某些算法。
(5)算法的工作过程,尽可能详细说明。对工作过程中比较难于理解的某些算法,则通过实例,从头到尾地模拟算法的运行。因为这是学习、理解算法的关键,没有用实例来模拟算法的运行,学生学完了以后,对该算法也只能是懵懂的,不知其所以然。
(6)无论是算法的基本概念、算法复杂性的分析方法,还是算法的实现步骤,都尽可能提供大量实例加以解释说明。
本书先以最简单的穷举法为例,说明算法设计技术及算法分析的重要性;接着以排序问题中的一些基本算法和其他一些算法为例,说明算法复杂性的一般分析方法;然后以算法设计技术为纲,按照实现算法的思想方法、实现步骤、所涉及的数据结构、算法的具体描述及复杂性分析等几个方面,逐个介绍各种算法设计技术及其分析方法。
全书分为4篇。第1篇包括第1章和第2章,介绍算法设计与分析的基本概念。第1章介绍算法的定义及算法的时间复杂性的基本概念;第2章介绍算法时间复杂性的分析方法,并简单介绍与算法分析有关的最基本的数学工具。第2篇包括第3~9章,介绍算法设计的基本技术。第3章继续介绍排序问题和离散集合的操作,进一步对算法分析进行了阐述,并为下面各章中所涉及的问题作了技术上的准备;第4章介绍递归技术及分治方法,从理论上分析了分治算法的效率;第5章介绍贪婪法的设计方法及其正确性的证明;第6章介绍动态规划法的设计技术;第7章介绍回溯法的设计技术;第8章在回溯法的基础上介绍分支与限界方法的应用及其分析;第9章介绍3种类型的随机算法及其性能分析。第3篇包括第10~11章,涉及计算机应用领域里的一些算法。第10章介绍图和网络流的一些问题;第11章介绍计算几何中的一些问题。第4篇包括第12~15章,介绍算法设计与分析中的一些理论问题。第12章介绍NP完全问题;第13章介绍计算复杂性问题;第14章介绍下界理论问题;第15章介绍近似算法及其性能分析。
本书对第2版做了一些修订。感谢许存权、钟志芳、纪文远、苏明芳、邓艳诸位编辑为本书的出版付出的大量工作和努力,在此表示诚挚的谢意。
由于水平有限,书中难免存在不当之处,敬请读者指正。
编 者
目 录
第1篇 算法设计与分析的基本概念
第1章 算法的基本概念 2
1.1 引言 2
1.1.1 算法的定义和特征 2
1.1.2 算法设计的例子——穷举法 4
1.1.3 算法的复杂性分析 7
1.2 算法的时间复杂性 8
1.2.1 算法的输入规模和运行时间的阶 8
1.2.2 运行时间的上界——O记号 11
1.2.3 运行时间的下界——Ω记号 12
1.2.4 运行时间的准确界——Θ记号 13
1.2.5 O记号、Ω记号、Θ记号的性质 17
1.2.6 复杂性类型和o记号 18
习题 19
参考文献 20
第2章 算法的复杂性分析 21
2.1 常用的函数和公式 21
2.1.1 整数函数 21
2.1.2 对数函数 22
2.1.3 排列、组合和二项式系数 23
2.1.4 级数求和 24
2.2 算法的时间复杂性分析 25
2.2.1 循环次数的统计 26
2.2.2 基本操作频率的统计 29
2.2.3 计算步的统计 32
2.3 最好情况、最坏情况和平均情况分析 33
2.3.1 最好情况、最坏情况和平均情况 33
2.3.2 最好情况和最坏情况分析 34
2.3.3 平均情况分析 37
2.4 用生成函数求解递归方程 40
2.4.1 生成函数及其性质 40
2.4.2 用生成函数求解递归方程 43
2.5 用特征方程求解递归方程 46
2.5.1 k阶常系数线性齐次递归方程 47
2.5.2 k阶常系数线性非齐次递归方程 49
2.6 用递推方法求解递归方程 51
2.6.1 递推 52
2.6.2 用递推法求解变系数递归方程 52
2.6.3 换名 54
2.7 算法的空间复杂性 56
2.8 最优算法 57
习题 58
参考文献 60
第2篇 算法设计的基本技术
第3章 排序问题和离散集合的操作 62
3.1 合并排序 62
3.1.1 合并排序算法的实现 62
3.1.2 合并排序算法的分析 64
3.2 基于堆的排序 65
3.2.1 堆 66
3.2.2 堆的操作 67
3.2.3 堆的建立 70
3.2.4 堆的排序 73
3.3 基数排序 74
3.3.1 基数排序算法的思想方法 74
3.3.2 基数排序算法的实现 76
3.3.3 基数排序算法的分析 78
3.4 离散集合的Union_Find操作 79
3.4.1 用于Union_Find操作的数据结构 79
3.4.2 union、find操作及路径压缩 81
习题 84
参考文献 85
第4章 递归和分治 86
4.1 基于归纳的递归算法 86
4.1.1 基于归纳的递归算法的思想方法 86
4.1.2 递归算法的例子 87
4.1.3 排列问题的递归算法 91
4.1.4 求数组主元素的递归算法 95
4.1.5 整数划分问题的递归算法 98
4.2 分治法 100
4.2.1 分治法的例子 100
4.2.2 分治法的设计原理 104
4.2.3 快速排序 111
4.2.4 多项式乘积和大整数乘法 116
4.2.5 平面点集最接近点对问题 123
4.2.6 选择问题 130
4.2.7 残缺棋盘问题 136
习题 141
参考文献 143
第5章 贪婪法 145
5.1 贪婪法概述 146
5.1.1 贪婪法的设计思想 146
5.1.2 贪婪法的例子——货郎担问题 147
5.2 背包问题 148
5.2.1 背包问题贪婪算法的实现 148
5.2.2 背包问题贪婪算法的分析 150
5.3 单源最短路径问题 151
5.3.1 解最短路径的狄斯奎诺算法 151
5.3.2 狄斯奎诺算法的实现 153
5.3.3 狄斯奎诺算法的分析 155
5.4 最小花费生成树问题 156
5.4.1 最小花费生成树概述 156
5.4.2 克鲁斯卡尔算法 157
5.4.3 普里姆算法 161
5.5 霍夫曼编码问题 165
5.5.1 前缀码和最优二叉树 165
5.5.2 霍夫曼编码的实现 169
习题 171
参考文献 173
第6章 动态规划 174
6.1 动态规划的思想方法 174
6.1.1 动态规划的最优决策原理 174
6.1.2 动态规划实例——货郎担问题 175
6.2 多段图的最短路径问题 177
6.2.1 多段图的决策过程 178
6.2.2 多段图动态规划算法的实现 180
6.3 资源分配问题 181
6.3.1 资源分配的决策过程 182
6.3.2 资源分配算法的实现 184
6.4 设备更新问题 187
6.4.1 设备更新问题的决策过程 187
6.4.2 设备更新算法的实现 190
6.5 最长公共子序列问题 192
6.5.1 最长公共子序列的搜索过程 192
6.5.2 最长公共子序列算法的实现 195
6.6 0/1背包问题 196
6.6.1 0/1背包问题的求解过程 196
6.6.2 0/1背包问题的实现 198
6.7 RNA最大碱基对匹配问题 199
6.7.1 RNA最大碱基对匹配的搜索过程 200
6.7.2 RNA最大碱基对匹配算法的实现 203
习题 205
参考文献 207
第7章 回溯 208
7.1 回溯法的思想方法 208
7.1.1 问题的解空间和状态空间树 208
7.1.2 状态空间树的动态搜索 209
7.1.3 回溯法的一般性描述 211
7.2 n皇后问题 213
7.2.1 n皇后问题的求解过程 213
7.2.2 n皇后问题算法的实现 215
7.3 图的着色问题 217
7.3.1 图着色问题的求解过程 218
7.3.2 图的m着色问题算法的实现 220
7.4 哈密尔顿回路问题 222
7.4.1 哈密尔顿回路的求解过程 222
7.4.2 哈密尔顿回路算法的实现 224
7.5 0/1背包问题 225
7.5.1 回溯法解0/1背包问题的求解过程 226
7.5.2 回溯法解0/1背包问题算法的实现 229
7.6 回溯法的效率分析 231
习题 234
参考文献 235
第8章 分支与限界 236
8.1 分支与限界法的基本思想 236
8.2 作业分配问题 238
8.2.1 分支限界法解作业分配问题的思想方法 238
8.2.2 分支限界法解作业分配问题算法的实现 241
8.3 单源最短路径问题 244
8.3.1 分支限界法解单源最短路径问题的思想方法 244
8.3.2 分支限界法解单源最短路径问题算法的实现 246
8.4 0/1背包问题 248
8.4.1 分支限界法解0/1背包问题的思想方法和求解过程 249
8.4.2 0/1背包问题分支限界算法的实现 251
8.5 货郎担问题 254
8.5.1 费用矩阵的特性及归约 254
8.5.2 界限的确定和分支的选择 256
8.5.3 货郎担问题的求解过程 259
8.5.4 几个辅助函数的实现 262
8.5.5 货郎担问题分支限界算法的实现 268
习题 271
参考文献 272
第9章 随机算法 273
9.1 随机算法概述 273
9.1.1 随机算法的类型 273
9.1.2 随机数发生器 274
9.2 舍伍德算法 275
9.2.1 随机快速排序算法 275
9.2.2 随机选择算法 277
9.3 拉斯维加斯算法 280
9.3.1 字符串匹配 280
9.3.2 整数因子 284
9.4 蒙特卡罗算法 285
9.4.1 数组的主元素问题 285
9.4.2 素数测试 287
习题 290
参考文献 291
第3篇 计算机应用领域的一些基法
第10章 图和网络问题 294
10.1 图的遍历 294
10.1.1 图的深度优先搜索遍历 294
10.1.2 图的广度优先搜索遍历 299
10.1.3 无向图的接合点 301
10.1.4 有向图的强连通分支 305
10.2 网络流 308
10.2.1 网络流的概念 308
10.2.2 Ford_Fulkerson方法和最大容量增广 312
10.2.3 最短路径增广 315
10.3 二分图的最大匹配问题 320
10.3.1 预备知识 321
10.3.2 二分图最大匹配的匈牙利树方法 323
习题 329
参考文献 331
第11章 计算几何问题 332
11.1 引言 332
11.2 平面线段的交点问题 334
11.2.1 寻找平面线段交点的思想方法 335
11.2.2 寻找平面线段交点的实现 337
11.3 凸壳问题 342
11.3.1 凸壳问题的格雷厄姆扫描法 343
11.3.2 格雷厄姆扫描法的实现 344
11.4 平面点集的直径问题 346
11.4.1 求取平面点集直径的思想方法 346
11.4.2 平面点集直径的求取 348
习题 350
参考文献 351
第4篇 算法设计与分析的一些理论问题
第12章 NP完全问题 354
12.1 P类和NP类问题 355
12.1.1 P类问题 355
12.1.2 NP类问题 356
12.2 NP完全问题 358
12.2.1 NP完全问题的定义 358
12.2.2 几个典型的NP完全问题 360
12.2.3 其他NP完全问题 366
12.3 co_NP类和NPI类问题 366
习题 369
参考文献 370
第13章 计算复杂性 371
13.1 计算模型 371
13.1.1 图灵机的基本模型 371
13.1.2 k带图灵机和时间复杂性 374
13.1.3 离线图灵机和空间复杂性 376
13.1.4 可满足性问题和Cook定理 379
13.2 复杂性类型之间的关系 381
13.2.1 时间复杂性和空间复杂性的关系 382
13.2.2 时间谱系定理和空间谱系定理 384
13.2.3 填充变元 389
13.3 归约性关系 391
13.4 完备性 394
13.4.1 NLOGSPACE完全问题 394
13.4.2 PSPACE完全问题和P完全问题 396
习题 397
参考文献 398
第14章 下界 399
14.1 平凡下界 399
14.2 判定树模型 399
14.2.1 检索问题 400
14.2.2 排序问题 401
14.3 代数判定树模型 402
14.3.1 代数判定树模型及下界定理 402
14.3.2 极点问题 404
14.4 线性时间归约 405
14.4.1 凸壳问题 406
14.4.2 多项式插值问题 406
习题 408
参考文献 408
第15章 近似算法 409
15.1 近似算法的性能 409
15.2 装箱问题 410
15.2.1 首次适宜算法 411
15.2.2 最适宜算法及其他算法 412
15.3 顶点覆盖问题 414
15.4 货郎担问题 416
15.4.1 欧几里得货郎担问题 417
15.4.2 一般的货郎担问题 419
15.5 多项式近似方案 419
15.5.1 0/1背包问题的多项式近似方案 420
15.5.2 子集求和问题的完全多项式近似方案 423
习题 425
参考文献 426
参考文献 427