算法 | 什么是时间复杂度?时间复杂度是如何计算出来的?

238 阅读3分钟

开启掘金成长之旅!这是我参与「掘金日新计划 · 12 月更文挑战」的第29天,点击查看活动详情

前言

本文主要介绍时间复杂度的基本概念以及场景算法的时间复杂度。

时间复杂度是用来描述发生了多少次常数操作的指标。

常数操作

如果某个操作跟数量的大小没有关系,每次都是固定时间的操作,这种操作叫做常数操作。

比如,1 + 110000 + 10000 a + b,这些操作经历的过程都是一样的,都是加法操作,这个操作时间是固定的,所以这个加法操作就是常数操作。

再比如,有一个长度为10000的数组,从数组中取出第10位元素和取出1000位元素,这两个操作的时间也是大致一致的,这种操作也叫做常数操作。

在执行某一个方法时,执行一行代码,如果这行代码的执行时间是固定的,那么这行代码就为常数操作;如果这行代码的执行时间跟数据量有关系,那么这行代码就不是常数操作。

时间复杂度

以冒泡排序为例,假如有一个长度为8的数组,在执行冒泡排序时过程如下:

第1轮,第0位置和第1位置的数据相比较,如果前面比后面大,就进行交换;第1位置和第2位置比较,如果前面比后面大,就进行交换;以此类推,第1轮结束后,最大值就来到了第7位置。

第2轮,第0位置和第1位置的数据相比较,如果前面比后面大,就进行交换;第1位置和第2位置比较,如果前面比后面大,就进行交换;以此类推,第1轮结束后,最大值就来到了第6位置。

以此类推,直到整个数组是有序的。

冒泡排序时间复杂度

那么,冒泡排序的时间复杂度是如何计算的呢?

相邻两个元素比较,这个操作每次都是一样的,是常数时间的操作,记为A操作。

对于冒泡排序,第1轮进行了7次比较操作,第2轮进行了6次比较操作,第3轮进行了5次比较操作,...。

这些操作是等差数列,等差数列公式为:

Sn = na1 + n(n1)2\frac{n*(n - 1)}{2} * d

其中,a1和d都是常数操作。

对公式化简一下就是:

Sn = n22\frac{n^2}{2} - (d2\frac{d}{2} - a1)n

时间复杂度就是整个表达式中最高阶项,用O表示。也就是说时间复杂度不关心低阶项,也不关心常数项,只关心最高阶项。

为什么只关心最高阶项?因为当数据量足够大时,低阶项和常数项和最高阶项比起来太微不足道了。

比如冒泡排序的时间复杂度为O(n2)。

冒泡排序的表达式可以表示为a*n2 + b * n + c, 其中a、b、c都为常数。

在估算时间复杂度时,要按照最差的情况来进行估算。

常数的时间复杂度为O(1)。

时间复杂度排序

常见的算法时间复杂度由小到大依次为:Ο(1)<Ο(logN)<Ο(N)<Ο(NlogN)<Ο(N2)<Ο(N3)< Ο(Nk) < Ο(2N) < Ο(3N) < Ο(kN) < Ο(N!)。

常见排序算法时间复杂度

排序算法时间复杂度
选择排序Ο(N2)
插入排序Ο(N2)
冒泡排序Ο(N2)
希尔排序Ο(Ns) 1<s<2
快速排序Ο(N2)
堆排序Ο(NlogN)
归并排序Ο(NlogN)