在最坏的情况下,分解Fizzbuzz所需的成本和时间

时间:2014-06-26 06:19:46

标签: algorithm time-complexity fizzbuzz

Fizz-Buzz函数(伪代码)采用任何正整数 n 。我对if-else语句所需的成本和时间的代数分解特别好奇。我知道最糟糕的情况是运行时间为O(n)。

Fizz-Bizz(n)
  for i = 1 to n
    if (n % 3 == 0)
      print "fizz"
    if (n % 5 == 0)
      print "buzz"
    if (n % 3 != 0 and n % 5 != 0)
      print n

另一种算法的细分示例:enter image description here

1 个答案:

答案 0 :(得分:2)

时间复杂度为O(n),因为if语句对此没有实际影响。 if语句的复杂性在足够大的数据集上是恒定的。

if语句实际上可能在迭代中执行不同数量的工作,其中您有三个或五个的倍数但是,每个循环迭代的额外工作量不依赖于n。实际上,随着n变大,它平均变为常数。

  

另外,我认为代码可能是错误的。在十五的倍数时,它应打印fizz buzz

如果要在编辑级别(添加的细分)中执行此操作,则只需为每个语句分配一个任意成本ci(对于该语句的单次执行,此成本是常量然后计算出每个语句的运行次数。

例如,第一个if序列运行n次,print "fizz"运行三分之一,n/3。所以你最终得到了这样的表:

                           cost   times
Fizz-Buzz(n)
  for i = 1 to n           c1     n
    if (n % 3 == 0)        c2     n
      print "fizz"         c3     n / 3       [call this a]
    else
      if (n % 5 == 0)      c4     n - a
        print "buzz"       c5     (n - a) / 5 [call this b]
      else
        print n            c6     n - a - b

根据您的示例添加所有这些(用n代替ab),最后,你仍然最终得到依赖于n的东西,因此是O(n)算法。它看起来像是:

  c1*n + c2*n + c3*n/3   + c4*(n-a)   + c5*(n-a)/5     + c6*(n-a-b)
= c1*n + c2*n + (c3/3)*n + c4*(n-n/3) + (c5/5)*(n-n/3) + c6*(n-n/3-(n-n/3)/5)
= c1*n + c2*n + (c3/3)*n + c4*(2/3)*n + (c5/5)*(2/3)*n + c6*(n-n/3-(n-n/3)/5)
= c1*n + c2*n + (c3/3)*n + (c4*2/3)*n + (c5*2/15)*n    + c6*(n*8/15)
= c1*n + c2*n + (c3/3)*n + (c4*2/3)*n + (c5*2/15)*n    + (c6*8/15)*n

   /             1         2             2                8    \
= ( c1  + c2   + - c3    + - c4       + -- c5          + -- c6  ) * n
   \             3         3            15               15    /

括号内的所有值实际上都是常量(因为它们是常量的倍数)所以整个事物是n的常数乘数。

现在,如果你发现上述等式中的一个小错误,我就不会感到惊讶了 - 我已经好几年没有做过这个级别的数学了,我很可能如果这是为了完成家庭作业,你会尝试复制它: - )

但是你唯一可能发现的错误就是常数乘数本身的。它仍然是某些描述的常量乘数,我保证。