一、分治法(递归算法)
说明:许多算法在结构上是递归的,为了解决某一问题,算法需要一次或多次递归的调用自身以解决紧密相关的若干子问题,这些算法遵循分治法的思想:将原问题分解为几个规模较小但类似于原问题的子问题,递归的求解这些子问题然后在合并这些子问题的解来建立原问题的解。
分治模式在每层递归时都有三个步骤:
1)分解,分解原问题为若干子问题,这些子问题是原问题规模较小的实例。
2)解决,解决这些子问题,递归的求解这些子问题。当子问题的规模足够小则直接求解。
3)合并,这些子问题的解构成原问题的解。
二、动态规划
动态规划(dynamic programming)与分治方法相似,都是组合子问题的解来求解原问题。分治方法将问题划分为互不相交的子问题,递归的求解子问题,再将他们的解组合起来,求出原问题的解。与之相反,动态规划应用于子问题重叠的情况,即不同子问题具有公共的子子问题(子问题的求解是递归进行的),将其划分为更小的子子问题。而动态规划算法对每个子子问题只求解一次,将其解保存在一个表格中,从而无需每次求解一个子子问题时都重新计算,避免了这种不必要的计算工作。
动态规划方法通常用来求解最优化的问题,这类问题可以有很多可行解,我们希望寻找具有最优值的解,称这样的解为问题的一个最优解,因为可能有多个解达到最优值。
应用动态规划求解问题的一般条件
1)最优子结构
如果一个问题的最优解包含其子问题的最优解,称此问题具有最优子结构性质。(具有最优子结构可能也可以应用贪心策略)
2)重叠子问题
子问题空间足够小,即问题的递归算法会反复的求解相同的子问题,而不是一直生成新的子问题。不同子问题的总数是输入规模的多项式函数为好。如果递归算法反复求解相同的子问题,称最优化问题具有重叠子问题性质。与之相对,适合用分治方法求解的问题通常在递归的每一步都生成全新的子问题。动态规划算法利用重叠子问题的性质,对每个子问题求解一次,将解存入一张表中,当再次需要这个子问题时直接查表,每次查表的代价为常量时间。
三、贪心算法
贪心算法是通过做出一系列选择来求出问题的最优解,在每个决策点,他做出当时看起来最佳的选择。这种启发式策略并不保证可以得到最优解,但对有些问题确实有效。
使用贪心选择的两个条件:
1)局部最优,通过做出局部最优选择来构造全局最优解,即对于最优化问题,通过贪心选择局部最优,只剩下一个子问题需要求解。
2)最优子结构,和动态规划问题相似,一个问题的最优解包含子问题的最优解。
小结:
在每个贪心算法之下都有一个对应的动态规划算法。对于贪心算法,确定规则的关键因素和所求问题的关键因素相一致,比如活动集合选择,就将按照活动结束时间排序。哈夫曼编码需要将用词频率低的词编码长度比较长,就按照频率进行二叉树构造。
在此算法中介绍了哈夫曼编码,主要是通过对频率排序,构造二叉树。感觉这种模型,适合于访问频率低的数据需要放到树底下的这种情况。