目录:
1.衡量一个算法的好坏
2.时间复杂度
3.时间复杂度的大O渐进表示法
4.时间复杂度的:最优、平均、最差情况,为什么时间复杂度看的是最差情况
5.求解:二分查找、递归求阶乘、递归斐波那契的时间复杂度
6.空间复杂度
7.求空间复杂度?普通函数& 递归函数
8.分析递归斐波那契数列的:时间、空间复杂度,并对其进行优化,伪递归优化->循环优化
1.针对一个问题可以有很多种的算法方法来解决问题,当然我们最喜欢的还是最简单的、最高效的。如何衡量算法的好坏,是学习算法的重要基础。
1.)最初,用所需要的计算时间来衡量一个算法的好坏
2.)但不同的是机器相互之间无法比较
3.)需要用独立于具体计算机的客观衡量标准
a.)问题的规模
b.)基本运算
c.)算法的计算量函数
2.时间复杂度
算法的时间复杂度是一个函数,他定性描述该算法的运行时间。这是一个代表算法输入值的字符串的长度的函数。时间复杂度常用大O符号表示,不包括这个函数的低阶项和首阶项系数。使用这种方法时,时间复杂度可被称为是渐进的,亦即考察输入值大小趋近无穷时的情况。

3.大O的渐进表示法
实际中我们计算时间复杂度时,并不一定要计算精确的执行次数而只需大概执行次数,这里我们使用大O的渐进表示法
大O(Big O notation):用于描述函数渐进行为的数学符号。
推导大O阶方法:
1.)用常数1取代运行时间中的所有加法常数。
2.)在修改后的运行次数中,只保留最高阶项。
3.)如果最高阶项存在且不为1,则去除与这个项目的常数,得到的结果就是大O阶。
大O的渐进表示法去掉那些对结果影响不大的项,简洁明了的表示出执行次数,另外有些算法的时间复杂度存在最好、平均、最坏情况:
最坏情况:任意输入规模的最大运行次数(上界)
平均情况:任意输入规模的期望运行次数
最好情况:任意输入规模的最小运行次数(下界)
eg.在一个长度为N数组中搜索一个数据x(最好情况:1次找到;最坏情况:N次找到)
4.时间复杂度的检测
时间复杂度要看最坏的情况,为什么呢?
最坏情况下的时间复杂度称最坏时间复杂度,一般不特别说明,讨论的时间复杂度均是最坏情况下的时间复杂度。
这样做的原因:最坏情况下的时间复杂度是算法在任何输入示例上运行时间的上界,这就保证了算法的运行时间不会比任何更长。
例1;变量计数之一 (1) x = 0; y = 0; (2) for (k - 1; k <= n; k++) (3) x++; (4) for (i = 1; i <= n; i++) (5) for (j = 1; j <= n; j++) (6) y++;
一般情况下,对步进循环语句只需要考虑循环体中语句的执行次数,忽略该语句中步长加1、终值判断、控制转移等成分。因此,以上程序段中频度最大的语句是(6),其频度为f(n)=n2,所以该程序段时间复杂度为T(n)=O(n2)。
当有若干个循环语句时,算法的时间复杂度是由嵌套层数最多的循环语句中最内层语句的频度f(n)决定的。
例2:变量计数之二。 (1)x = 1; (2) for (i = 1; i <= n; i++) (3) for (j = 1; j <= i; j++) (4) for (k = 1; k <= j; k++) (5) x++;
该程序段中频度最大的语句是(5),内循环的执行次数虽然与问题规模n没有直接关系,但是却与外层循环的变量取值有关,而最外层循环的次数直接与n有关,因此可以从内层循环向外层分析语句语句(5)的执行次数。
则该程序段的时间复杂度为T(n)=O(n3/6+低次项)=O(n3)。
5.空间复杂度
空间复杂度(Space Complexity)是对一个算法在运行过程中临时占用存储空间大小的量度,记做S(n)=O(f(n))。比如直接插入排序的时间复杂度是O(n*2),空间复杂度是O(1)。而一般的递归算法就要有O(n)的空间复杂度了,因为每次递归都要存储返回信息。一个算法的优劣主要从算法的执行时间和所占用的存储空间两个方面衡量。空间复杂度计算规则基本跟时间复杂度类似,也用大O渐进法表示。
斐波那契数的空间复杂度1:
long long* Fib(size_t n){ if (n == 0) return NULL; long long* fibArray = new long long[n + 1]; fibArray[0] = 0; fibArray[1] = 1; for (int i = 2; i <= n; ++i){ fibArray[i] = fibArray[i - 1] + fibArray[i - 2]; } return fibArray; }
以上fib程序的空间复杂度为O(n-1) = O(n)。
long long Fib(long long First, long long Second, int N){ if (N < 3) return 1; if (N == 3) return First + Second; return Fib(Second, First + Second, N - 1) }
以上是优化过的fib程序空间复杂度为O(1)。