下面我有一个插入排序算法,它包含嵌套的for循环:
public InsertionSort( AnyType [] a ){
int m;
for( int n = 1; n < a.length; n++ ){
AnyType temp = a[n];
for( m = n; m > 0 && tmp.compareTo( a[ m - 1] ) <= 0; m-- )
a[ m ] = a[ m - 1 ];
a[ m ] = temp;
}
}
第一个循环有运行时间O(N),第二个循环是O(N ^ 2),所以嵌套循环中的总运行时间应该是O(N * N ^ 2 = N ^ 3),我是对的?但我知道最坏的情况应该是插入排序中的O(N ^ 2)这一事实,但是我的老师通过替换[m - 1])&lt; = 0来改变这本书提供的代码段,而不是使用[m-1])&lt;所以我很困惑,为什么我计算一个比最坏情况更糟的情况。有人帮吗?提前谢谢。
答案 0 :(得分:1)
第二个是O(N ^ 2)
那是错的。看看如何。
考虑a.length = N
,TC应为O(N^2)
。
因为(1 + 2 + 3 + ... + N-1) = N(N-1)/2 = O(N^2)
内环比以前的时间运行1次。
[1, 1]
[2, 1]
[3, 1]
...
[N-1, 1]
答案 1 :(得分:0)
for(int n = 1; n&lt; a.length; n ++){
在上面的这一行中,你将经历数组 n - 1次(因为你从索引1开始一直到a.length -1),因此 O( N)强>
for(m = n; m> 0&amp;&amp; tmp.compareTo(a [m - 1])&lt; = 0; m--)
在这个内循环中,你从n开始然后向下移动,所以在最坏的情况下,你将从当前值 n一直下降到1 ,从而执行进行比较。
因此,我们可以在最坏情况下看到以下内容:
因此,您总共执行 1 + 2 + 3 + 4 + ... N - 1 操作,等于:
(N)(N-1)/ 2 = O(N ^ 2)
答案 2 :(得分:0)
让我们使代码更简单,如下所示。
public InsertionSort( AnyType [] a ){
// A value n
for( ; n < length ; ){
// A value m
for( ; m < someLength ; ) {
// do something.
}
}
}
如你所说,'someLength'可以是n-1中的1。
但是让我们看看内循环方面的代码。
blahblah
for( ; m < someLength ; ) {
// do something.
}
blahblah
它只运行一些长度 - m(或者如果它低于0)则运行
,这是线性的
,表示为N(对于O(N))。
还有一件事。
没有外环,1 + 2 + 3 + 4 + ... + n-1不能发生,可以吗?
那你为什么要把它们算作内循环的复杂性呢?