数据结构与算法学习之路1--复杂度分析

206 阅读1分钟

复杂度分析的定义及常见类型

复杂度分析指的是不使用具体的测试数据来粗略地估计算法的执行效率的方法。通常我们从时间复杂度和空间复杂度两个维度来进行复杂度分析。

  • 时间复杂度表示代码的执行时间随着数据规模的增长的变化趋势,也叫渐进时间复杂度。
  • 空间复杂度表示算法的存储空间与数据规模之间的增长关系,也叫做渐进空间复杂度。

大O表示法

我们分析一下下面这个求1,2,3...n的累加和的执行时间。

function add($n){
    $sum = 0;
    $i = 1;
    for ($i; $i<=$n; $i++){
        $sum = $sum + $i;
    }
    return $sum;
}

在CPU的角度来看每一行代码都是进行:读数据-运算-写数据的类似操作,因此我们可以粗略地认为每行代码的执行时间是一样的为unit_time。上面的代码中我们可以看到第2行和第3行都只运行了一次,第4行和第5行都重复运行了n遍,因此上面这段代码的运行总时间大约为(2n+2)*unit_time。我们可以看出来代码的总执行时间和每行代码的的执行次数成正比。 我们把代码的执行总时间记作T(n),数据规模记作n,每行代码执行的次数的和记作f(n),则T(n) = O(f(n)),O就表示正比。上面那个代码用大O表示法为T(n) = O(2n+2)。

时间复杂度分析的几个方法

  • 只关注循环执行次数最多的一段代码
  • 总得时间复杂度等于量级最大的那段代码的时间复杂度
  • 嵌套代码的时间复杂度等于嵌套内外代码复杂度的成绩

常见的几种复杂度以及示例代码

实际开发过程中我们使用的常见的几种复杂度从低阶到高阶有:O(1)、O(logn)、O(n)、O(nlogn)、O(n^{2})

O(1)

$i = 1;
$j = 2;
$sum = $i + $j;

O(logn)

$i = 1;
while($i <= $n){
    $i = $i * 2;
}

O(n)

$sum = 0;
$i = 1;
for ($i; $i <= $n; $i++){
    $sum = $sum + $i;
} 

O(nlogn)

$sum = 0;
$i = 1;
for ($i; $i <= $n; $i++){
    $j = 1;
    while($j <= $n){
        $j = $j * 2;
    }
}

O(n^2)

$i = 1;
$j = 1;
$sum = 0;
for ($i; $i <= $n; $i++){
    for($j; $j <= $n; $j++) {
        $sum = $i + $j;
    }
}