代码增长的算法顺序

时间:2014-03-05 08:48:53

标签: algorithm discrete-mathematics

我正在网上参加一门课程并坚持以下问题。以下代码片段的最坏情况运行时间的增长顺序是N?

的函数
int sum = 0;
for (int i = 1; i <= N*N; i++)
    for (int j = 1; j <= i; j++)
        for (int k = 1; k <= j; k++)
            sum++;

我认为它是N^4的顺序,但似乎这个答案是错误的。你能解释一下吗?

4 个答案:

答案 0 :(得分:6)

它是O(N^6)的顺序。您应该注意,每个循环都只是为复杂性添加了一个订单N。考虑以下示例:

int sum = 0;
for (int i = 1; i <= M; i++)
    for (int j = 1; j <= i; j++)
        for (int k = 1; k <= j; k++)
            sum++;

你应该能够很容易地发现它是O(M^3)的顺序,所以如果你替换M=N^2,那么你就会得到答案。关键点在于,在这种情况下,每个内部循环的顺序为O(N^2),但不是O(N)

答案 1 :(得分:3)

我们用n = N^2表示。然后,每次k <= i <= j时都会执行循环。这将大约n^3/6次。因此,运行时为O(n^3)= O(N^6)


解释:暂时忽略k==ij==ij==k的情况, 我们从6个不同的三元组中选择1个:

 (a1,a2,a3)
 (a1,a3,a2)
 (a2,a1,a3)
 (a2,a3,a1)
 (a3,a2,a1)
 (a3,a1,a2)

总体而言,有n^3三倍。 6个三元组中只有一个服从命令。

答案 2 :(得分:2)

内部循环的一次运行恰好sum次增加j次。

中间循环的一次运行恰好i次调用内循环,j1之间的值i。因此,sum恰好1+2+3+...i次增加i.(i+1)/2次,这是众所周知的“三角数”公式。{/ p>

外部循环恰好N^2次调用中间循环(让我们将其表示为M),i1之间的值为M (包括的)。因此,sum恰好1+3+6+...M.(M+1)/2次增加M.(M+1).(M+2)/6次。同样,这是sum,由不太知名的“四面体数”公式(http://en.wikipedia.org/wiki/Tetrahedral_number)。

总而言之,N^2.(N^2+1).(N^2+2)/6的最终价值为O(j)

以渐近项思考,内循环为O(i^2),中间循环为O(M^3)(通过求和),外循环为O(N^6)(通过求和),即n^k

另请参阅Faulhaber的公式,其中显示O(N^(k+1))的总和为{{1}}(http://en.wikipedia.org/wiki/Faulhaber%27s_formula)。

答案 3 :(得分:1)

最内层(k)循环的任何给定运行都具有与j成比例的时间,但是我们必须为j = 1到j = i中的每一个执行其中一个,并且总和1 + 2 + ... +我像i ^ 2一样成长。因此,对于任何给定的 i,我们有一个O(i ^ 2)运行时间,但当然我们必须处理i = 1到i = N ^ 2。 i ^ 2的总和为i = 1到N ^ 2 happens to grow like N^6