嵌套for循环的时间复杂度

时间:2018-12-18 07:27:40

标签: c algorithm time time-complexity big-o

下面的代码块的时间复杂度是多少 无效函数(int n)。

我的尝试是,最外层的循环将运行n / 2次,而内层的两个将运行2 ^ q次。然后我用n等于2 ^ q并以2为底得到q为1/2(log n)。乘以时间复杂度,我得到的值为O(nlog(n)),而答案是O(nlog ^ 2(n) ))。

void function(int n) { 
    int count = 0; 
    for (int i=n/2; i<=n; i++)  
        for (int j=1; j<=n; j = 2 * j)
            for (int k=1; k<=n; k = k * 2) 
                count++; 
} 

3 个答案:

答案 0 :(得分:6)

是时候应用理解循环嵌套的黄金法则了:

  

如有疑问,请由内而外!

让我们从原始的循环巢开始吧:

    for (int i=n/2; i<=n; i++)  
        for (int j=1; j<=n; j = 2 * j)
            for (int k=1; k<=n; k = k * 2) 
                count++; 

该内部循环将运行Θ(log n)次,因为在该循环的m次迭代之后,我们看到k = 2 m ,并且当k≥n = 2 lg n时停止。因此,我们用以下更简单的表达式替换该内部循环:

    for (int i=n/2; i<=n; i++)  
        for (int j=1; j<=n; j = 2 * j)
            do Theta(log n) work;

现在,看看最里面的剩余循环。通过与之前完全相同的推理,我们看到此循环也运行Θ(log n)次。由于我们进行了每次都进行Θ(log n)迭代的Θ(log n)迭代,因此我们看到可以用以下更简单的循环代替此循环:

    for (int i=n/2; i<=n; i++)
        do Theta(log^2 n) work;

在这里,外循环运行Θ(n)次,因此总体运行时间为Θ(n log 2 n)。

我认为,根据您在问题中所说的话,您具有正确的见解,但只是忘记将对数项的两个副本相乘,两个内环各一个。

答案 1 :(得分:2)

您的代码中有3个嵌套循环。

  1. 第一个循环运行n/2次,在计算复杂度时几乎等于n。
  2. 第二个循环运行logn次。
  3. 第三次循环运行logn次。

因此,最终时间复杂度将为O( n * logn * logn ) == O(nlog^2n)
现在,您可能想知道如何记录两个内部循环的运行时复杂度。可以概括如下:
由于我们在每次迭代中都乘以2,因此我们需要q的值如下:
     n = 2 ^ q

两边都采用日志基础2

log2 n = log2 (2^q)
log2 n = q log2(2)
log2 n = q * 1 [ since, log2(2) is 1 ]

因此,q等于logn
因此,总体时间复杂度为:O(n*log^2n).

答案 2 :(得分:1)

第一个循环需要:n / 2

第二个循环:log(n)

第三循环:log(n)

请注意,由于内部循环的步数乘以2,因此在时间复杂度方面,它们各自的计数器呈指数增长,在n中达到log(n)

然后,还请注意,在这种情况下,可以安全地忽略诸如1/2的常量,其结果为O(n * log(n) *log(n)),因此:

  

O(nlog 2 n)