java代码的时间复杂度

时间:2012-08-12 19:42:53

标签: java algorithm time-complexity

我正在学习课程的算法课程,我坚持这个特殊的问题。我应该找到这段代码的时间复杂性。

int sum = 0

 for (int i = 1; i <= N*N; i = i*2)

  {
     for (int j = 0; j < i; j++)
           sum++; 
  }

我在eclipse中检查了它,对于N的任何值,sum语句的执行次数小于N

final value of sum:
for N=8 sum=3 
for N=16 sum=7 
for N=100000 sum=511

因此时间复杂度应小于N. 但是给出的答案是N提升到2的力量,怎么可能?

到目前为止我做了什么:

第一个循环将运行log(N ^ 2)次,因此第二个循环将执行1,2,3 .. 2 logN

4 个答案:

答案 0 :(得分:3)

第一个内环将是1 + 2 + 4 + 8 .. 2 ^ M,其中2 ^ M <&lt; = N * N.

2到N * N的幂之和约为2 * N * N或O(N ^ 2)

注意:当N = 100000时,N * N将溢出,因此其结果具有误导性。如果你认为溢出是问题的一部分,对于大数,总和是相当随机的,所以你可以争论它的O(1),即如果N = 2 ^ 15,N ^ 2 = 2 ^ 30并且总和将是整数.MAX_VALUE。没有更高的N值会得到更高的总和。

答案 1 :(得分:3)

这里存在很多混淆,但重要的是Big-O notation完全是关于增长率,或限制行为,正如数学家所说的那样。函数将在O(n * n)中执行意味着执行时间将比例如 n 更快地增加,但比例如 2 ^ n

在使用big-O notation进行推理时,请记住常量“不计算”。在这个特定问题上有一些问题。

  • 如果循环是常规for循环,那么N*N表达式会导致O(log n * n)复杂度...
  • ...但是,for循环增量为i = i*2,导致外循环执行大约log n,如果内循环的内容在a中运行,则函数将在O(log n)中时间独立于 n
  • 但同样,内循环运行时依赖于 n ,但它不会运行n * n,而是大致记录log(n * n)/ 2循环。记住“常量不计算”,我们最终得到O(n * n)。

希望这能解决问题。

答案 2 :(得分:2)

因此sum ++将执行1 + 2 + 4 + 8 + ... + N * N,总log2(N * N)次。几何级数之和1 *(1 - 2 ^ log2(N * N)/(1 - 2)= O(N * N)。

答案 3 :(得分:0)

你的外环是log(N ^ 2) - > 2 * log(N) - > log(N),你的内环是N ^ 2 / 2-> N ^ 2。因此,时间复杂度为N ^ 2 * log(N)。

关于基准测试,N = 8或N = 16的值是荒谬的,循环中的时间与设置JVM,缓存失败等相关是微不足道的。你必须:

从最大的N开始,并检查它的评估方式。

使用N的每个值进行多次运行。

认为时间复杂度是当N变得非常大时算法如何工作的度量。