一、定义
(1)如果一个问题的规模是n,解这一问题的某一算法所需要的时间为T(n),它是n的某一函数 T(n)称为这一算法的“时间复杂性”。我们常用大O表示法表示时间复杂性,称之为大O记法。
(2)一个问题本身也有它的复杂性,如果某个算法的复杂性到达了这个问题复杂性的下界,那就称这样的算法是最佳算法。常见的时间复杂度高低顺序如下:
O(1) 常数阶 < O(logn) 对数阶 < O(n) 线性阶 < O(nlogn) < O(n^2) 平方阶 < O(n^3) < O(2^n) < O(n!) < O(n^n)
二、时间复杂度计算步骤
⑴ 找出算法中的基本语句;
算法中执行次数最多的那条语句就是基本语句,通常是最内层循环的循环体。
⑵ 计算基本语句的执行次数的数量级;
只需计算基本语句执行次数的数量级,这就意味着只要保证基本语句执行次数的函数中的最高次幂正确即可,可以忽略所有低次幂和最高次幂的系数。这样能够简化算法分析,并且使注意力集中在最重要的一点上:增长率。
⑶ 用大Ο记号表示算法的时间性能。
将基本语句执行次数的数量级放入大Ο记号中。
如果算法中包含嵌套的循环,则基本语句通常是最内层的循环体,如果html" target="_blank">算法中包含并列的循环,则将并列循环的时间复杂度相加。
三、时间复杂度计算规则
(1)对于一些简单的输入输出语句或赋值语句,近似认为需要O(1)时间
(2)对于顺序结构,需要依次执行一系列语句所用的时间可采用大O下"求和法则"
求和法则:是指若算法的2个部分时间复杂度分别为 T1(n)=O(f(n))和 T2(n)=O(g(n)),则 T1(n)+T2(n)=O(max(f(n), g(n)))
特别地,若T1(m)=O(f(m)), T2(n)=O(g(n)),则 T1(m)+T2(n)=O(f(m) + g(n))
(3)对于选择结构,如if语句,它的主要时间耗费是在执行then字句或else字句所用的时间,需注意的是检验条件也需要O(1)时间
(4)对于循环结构,循环语句的运行时间主要体现在多次迭代中执行循环体以及检验循环条件的时间耗费,一般可用大O下"乘法法则"
乘法法则: 是指若算法的2个部分时间复杂度分别为 T1(n)=O(f(n))和 T2(n)=O(g(n)),则 T1*T2=O(f(n)*g(n))
(5)对于复杂的算法,可以将它分成几个容易估算的部分,然后利用求和法则和乘法法则技术整个算法的时间复杂度
我已经通过谷歌和堆栈溢出搜索,但我没有找到一个关于如何计算时间复杂度的清晰而直接的解释。 说代码像下面这样简单: 说一个像下面这样的循环: 这将只执行一次。 时间实际上被计算为而不是声明。
我在考虑如何正确计算这个函数的时间复杂度: 我假设它是 O(n),其中 n 是列表的长度。我们的 while 循环是 O(n),for 循环也是 O(n), 这意味着我们得到了 2*O(n),等于 O(n)。 我说的对吗?
我遇到了一个问题,需要计算非常大的阶乘的值。我用两种不同的方法在C中解决了这个问题,但只想知道我的复杂性分析是否准确。 在任何一种方法中,我都将非常大的数字表示为向量,其中表示最低有效数字,最后一个索引处的值表示最高有效数字。版本1的代码可以在这个要点中找到。 给定上面的代码,似乎是其中是给定的整数,是向量表示的数字。我的逻辑是,我们将执行一些与结果数字的长度成比例的步骤,以便生成一个表示的向量。
每个顶点可以连接到(V-1)个顶点,因此每个顶点的相邻边数是V-1。假设E代表连接到每个顶点的V-1条边。 查找和更新最小堆中每个相邻顶点的权重为O(log(V))+O(1)或 因此,从上面的步骤1和步骤2,更新顶点的所有相邻顶点的时间复杂度是e*(logV)。或. 因此所有V顶点的时间复杂度为V*(E*logv),即。 但Dijkstra算法的时间复杂度为O(ElogV)。为什么?
我正在尝试分析一个算法的时间复杂度。 下面的算法旨在只检查数组的一部分,所以如果它没有多大意义,请不要担心。 我对计算循环周围的时间复杂度很困惑,请看看我的评论。 这是否意味着我们有: T(N) = (C2 C4 C5)N (C1 C3 C6) T(N) = C7*N (C8) T(N)=N?? 循环中的所有内容都是*N? 先谢谢!
如何计算这些回溯算法的时间复杂度,它们是否具有相同的时间复杂度?如果不一样怎么办?请详细解释并感谢您的帮助。 我实际上有点困惑,对于断字(b),复杂度是O(2n),但对于哈密顿循环,复杂度是不同的,对于打印相同字符串的不同排列,以及对于解决n皇后问题,复杂度是不同的。