算法概述
英国数学家图灵提出的计算模型, 一个两端无限长的由小格子组成的带子,每个格子可以存储一个数,一个可以在带子左右移动的游标或者指针或者不如叫磁头(head), 磁头可读或修改格子里的数。
默认说的是确定性图灵机,和非确定性图灵机功能上等价
著名计算机科学家沃思提出了下面的公式: 程序 = 数据结构 + 算法;
实际上,一个程序应当采用结构化程序设计方法进行程序设计,并且用某一种计算机语言来表示。因此,可以用下面的公式表示: 程序 = 算法 + 数据结构 + 程序设计方法 + 语言和环境;
简单点的比如:递归、递推、迭代、穷举、概率算法、随机算法等
复杂些的比如:分治算法、贪心算法、动态规划、回溯法、分支限界等,后面会赘述一些这几种算法的基本思想与常见应用。
算法由三部分影响:
1. 存储结构
2. 算法的空间复杂度
3. 算法的时间复杂度
clock() :捕捉从程序开始运行到clock()被调用时所耗费的时间。这个 时间单位是clock tick,即“时钟打点”。
常数 CLK_TCK(或CLOCKS_PER_SEC) :机器时钟每秒所走的时钟打点数。
对于相同输入规模的不同实例,算法的基本运算次数也不一样,可定义两种时间复杂度
最坏情况复杂度 > 平均复杂度
上界、下界都有无穷个,但是太大的上界、太小的上界对我们分析算法的效率没有帮助,一般我们取最小的上界与最大的下界
当我们发现这个算法是 的时候,应该本能的想到有没有可能把它改进为 (尝试分治策略)
递归的时间复杂度一般稍微有点复杂,耐心一步一步分析带入、化简、计算
容易看出,前面的几类复杂度被分为两种级别,其中后者的复杂度无论如何都远远大于前者。像 等,我们把它叫做 多项式级复杂度 ,因为它的规模n出现在底数的位置;
另一种像是 和 等,它是 非多项式级的复杂度 ,其复杂度计算机往往不能承受。当我们在解决一个问题时,我们选择的算法通常都需要是多项式级的复杂度,非多项式级的复杂度需要的时间太多,往往会超时,除非是数据规模非常小。
对于同一个问题,不同的算法可能会产生不同的复杂度。最典型的例子就是排序,对于n个整数,选择排序和冒泡排序的复杂度为 ,快速排序的复杂度为 ,而使用基数排序的复杂度仅为 。