- 算法复杂度是什么?
是指算法在编写成可执行程序后,运行所需的内存资源和时间资源,主要通过时间复杂度和空间复杂度来表示。算法的复杂性体现在运行该算法时的计算机所需资源多少上,而计算机资源最重要的是时间和空间(寄存器)资源,因此分为空间复杂度和时间复杂度。
- 时间复杂度是什么?
是一个定性的描述算法运行时间的函数;是代表算法输入值的字符串的长度的函数(该句来自wiki pedia)
- 空间复杂度是什么?
是对一个算法在运行过程中临时占用存储空间大小的度量,即问题规模n的函数。
- 如何表示时间复杂度?
时间复杂度一般用O表示,不包括该复杂度函数的低阶项和系数项。也就是说,如果一个算法的时间复杂度是O(n)=5n3+ 3n,那么它的复杂度是O(n3)
- 如何表示空间复杂度
我们一般讨论的也是渐进空间复杂度,记作S(n)=O(f(n)),比如直接插入排序的时间复杂度是O(n^2),空间复杂度是O(1),递归算法的空间复杂度是O(n),因为每次递归都要返回数据。
当使用O(n)这种方式表示时间复杂度时,更多的是对真正的时间复杂度的一种渐进,模拟的是n趋于无穷大时的复杂度。
- 如何计算时间复杂度
- 估计算法的操作单元数量,每个单元的运行时间都相同。总运行时间和算法的操作单元数量最多差一个常量系数。
- 相同数量级的不同输入值也可能造成算法运行时间不同,所以用算法的最坏情况复杂度T(n),定义为任何大小的输入n所需要的最大时间(上界)
- 一个算法中某个语句的执行次数叫做语句频度或者时间频度,记为T(n)
- 几种时间复杂度:
常数时间:如果对于一个算法,T(n)的上界与输入大小无关,则称其具有常数时间,记作O(1),如访问数组内的单个元素。
线性时间:如果需求是找到无序数组中的最小元素,因为需要遍历所有元素来找到最小值,是一个线性时间操作,记作O(n)
对数时间:计算机采用二进制计数,所以对数一般以2为底。由于不同的对数公式只有底数不同,而且都是常数,所以O计法中将这个底数抛弃,记为O(logn),常见的有二叉树相关操作和二分搜索。对数时间中每增加一个输入,所需额外计算时间变小。
指数时间:一个问题求解所需要的计算时间n随着n的增加呈指数型增长
- 如何计算空间复杂度?
空间复杂度的计算主要考虑三个方面:
- 存储算法本身所占的存储空间
- 算法的输入输出数据所占用的存储空间
- 算法在运行过程中临时占用的存储空间
其中,算法的输入输出数据是由要解决的问题决定的,通过参数表由调用函数传递而来,不随着算法的不同而改变。
存储算法本身所用的存储空间与算法长度成正比,要压缩这部分就要写出较短的代码
- 常用算法时间复杂度
Dijkstra: O(n2) 适用于 权值为非负 的图的单源最短路径,用斐波那契堆的复杂度O(E+VlgV)
K shortest path: (from wiki) The running time complexity is pseudo-polynomial, being O(kn(m + n log n)) (where m and n represent the number of edges and vertices, respectively).
(https://en.wikipedia.org/wiki/K_shortest_path_routing)
Yen, J. Y. (1971). "Finding the k-Shortest Loopless Paths in a Network". Management Science. 1 7 (11): 712–716. doi:10.1287/mnsc.17.11.71
A new implementation of Yen’s ranking loopless paths algorithm (https://estudogeral.uc.pt/bitstream/10316/7763/1/obra.pdf)
BellmanFord:适用于权值有负值的图的单源最短路径,并且能够检测负圈,复杂度O(VE)
SPFA:适用于权值有负值,且没有负圈的图的单源最短路径,论文中的复杂度O(kE),k为每个节点进入Queue的次数,且k一般<=2,但此处的复杂度证明是有问题的,其实SPFA的最坏情况应该是O(VE).
Floyd:每对节点之间的最短路径。Floyd-Warshall算法的时间复杂度为O(N3),空间复杂度为O(N2)。
————————————————
版权声明:本文为博主「雪飞静」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。