冒泡排序与选择排序相比如何?

时间:2010-12-30 09:46:14

标签: algorithm sorting

哪种排序技术更快:泡泡或选择排序,为什么?两者都同样有效吗?

8 个答案:

答案 0 :(得分:12)

Wikipedia说(强调补充):

  

简单平均情况Θ(n 2 )   算法,几乎选择排序   总是优于冒泡排序和   gnome排序,但一般   优于插入排序。   插入排序非常相似   在第k次迭代之后,第一个k   数组中的元素已排序   订购。插入排序的优点是   它只扫描尽可能多的元素   它需要为了放置k + 1st   元素,而选择排序必须   扫描所有剩余的元素以查找   第k + 1个元素。

     

简单的计算表明   因此通常会插入排序   执行大约一半的比较   作为选择排序,虽然它可以   表现同样多或少得多   取决于阵列的顺序   在排序之前。它可以被视为   一些实时的优势   选择排序的应用程序   无论如何都表现相同   插入时的数组顺序   sort的运行时间可能会有所不同   相当。但是,这更多   通常是插入排序的一个优点   因为它运行得更有效率   如果数组已经排序或   “接近排序。”

     

虽然选择排序比较好   插入排序的数量   写(Θ(n)互换与Ο(n 2 )   交换),它几乎总是远远超过   (并且从不打败)写入次数   循环排序作为循环排序   理论上在数量上是最优的   写作如果这很重要   写得更多   比阅读昂贵,比如   EEPROM或闪存,每一个   写减少了生命周期   存储器中。

     

最后,选择排序很重要   在较大的阵列上优于Θ(n   log n)分而治之的算法   例如mergesort。但是,插入   排序或选择排序都是   对于小型阵列通常更快   (即少于10-20个元素)。一个   在实践中有用的优化   切换算法就是切换   插入排序或选择排序   对于“足够小”的子列表。

而且,维基百科bubble sort(重点补充):

  

冒泡排序有最坏情况和平均值   复杂性О(n 2 ),其中n是   被分类的项目数量。那里   存在许多排序算法   最糟糕的情况或   O(n log n)的平均复杂度。甚至   其他О(n 2 )排序算法,例如   作为插入排序,往往更好   性能比冒泡排序。   因此,冒泡排序不是一个   n是时的实用排序算法   大。

     

唯一显着的优势   冒泡排序超过了其他大多数   实现,甚至快速排序,但是   不插入排序,就是那个   检测列表的能力   排序有效地构建到   算法。泡泡排序的表现   在已经排序的列表上   (最好的情况)是O(n)。相比之下,大多数   其他算法,甚至那些算法   更好的平均案例复杂性,   执行他们的整个排序过程   在集合上,因此更复杂。   但是,不仅插入排序   也有这个机制,但它也   在列表上表现更好   基本上排序(有一个小的   反转次数)。

答案 1 :(得分:5)

与冒泡排序相比,选择排序执行的交换数量较少;因此,即使两种排序方法都是O(N 2 ),选择排序也会更快,更有效!

答案 2 :(得分:1)

冒泡排序算法被认为是最简单和最低效的算法,但与冒泡排序相比,选择排序算法是有效的。冒泡排序还会占用额外的空间来存储临时变量,并且需要更多的交换。

答案 3 :(得分:1)

在比较这两种算法时,我们必须考虑这些算法中发生的两种操作 i)比较 ii)交换 在比较运算的基础上,两者的效率均相同 但是如果您考虑交换操作,您会发现选择排序更为有效 考虑大小为100的降序数组,我们必须按升序对其进行排序 在此问题中,气泡排序将进行100 * 100 =(10000)个apprx交换操作,而在 SELCTION SORT 情况下,将仅进行100个交换操作,因为每个操作都进行选择排序迭代只有一次交换

答案 4 :(得分:0)

即使它们都具有可比较的,差的,最差的和平均的案例复杂性,但有certain points表明选择排序优于冒泡排序。

  

选择排序花费大部分时间   时间试图找到最低限度   元素在“未分类”的部分   阵列。它清楚地显示了相似性   在选择排序和泡沫之间   分类。冒泡排序“选择”了   每个最大剩余元素   阶段,但浪费了一些努力   传递一些命令“未分类”   阵列的一部分。

答案 5 :(得分:0)

尽管Senthil的link朝着正确的方向前进,但我似乎在这里或其他地方都找不到令人满意的解决方案。

这个问题最初让我感到困惑,因为可以通过在子数组(或链表等)通过后执行值交换失败来尽早终止外循环来优化冒泡排序。选择排序无法以这种方式提供帮助,那么为什么它会跑赢大市?两者在通用性上都很弱-O(n ^ 2)-那么为什么至少可以稍微改善一下呢?

答案完全基于对我自己和其他实现的检查,是气泡排序对每个单比较命中都会进行值交换(读,写,写)。选择排序仅记录新的边界值(最小值用于升序排序,最大值用于降序排序),然后在遍历结束时将其替换掉。

void swapInt(int *ptr1, int *ptr2) {
   int temp;

   temp = *ptr1;
   *ptr1 = *ptr2;
   *ptr2 = temp;
}

/* compare and swap over a shrinking sub-array */
void bubbleSortArray(int a[], const int aSize) {
   int unsorted, i, iMax = (aSize - 1);

   do {
      unsorted = 0;
      for (i = 0; i < iMax; i++) {
         if ( a[i] > a[i + 1] ) {
            unsorted = 1;
            /* swap every time comparison is true */
            swapInt(&a[i], &a[i + 1]);
         }
      }
      --iMax;
   } while (unsorted);
}

/* compare to find min value, write it before shrinking the sub-array */
void selectSortArray(int a[], const int aSize) {
   int i, j, mindex;

   for (i = 0; i < (aSize - 1); i++) {
      mindex = i;
      for (j = (i + 1); j < aSize; j++) {
         if ( a[j] < a[mindex] ) mindex = j;
      }
      /* swap after inner loop terminates */
      swapInt(&a[i], &a[mindex]);
   }
}

答案 6 :(得分:0)

气泡排序使用更多的交换时间,而选择排序避免了这种情况。

使用选择排序时,它最多交换n次。但是当使用冒泡排序时,它几乎交换n *(n-1)。显然,即使在内存中,读取时间也比写入时间短。比较时间和其他运行时间可以忽略。因此,交换时间是问题的关键瓶颈。

答案 7 :(得分:0)

在冒泡排序中,我们有更多的比较和交换。

在一个包含 10 个元素的数组中,我们在第一遍中有 9 次比较,在第二遍 7,6 中有 8 次比较,依此类推。在每 8 或 9 次比较中,我们只能交换元素。

在选择排序中,我们首先找到所有元素中的最小元素并将其放置在元素的 0 索引处。

两种算法的复杂度都是 O(n2),但在最坏的情况下,冒泡排序的复杂度为 O(n2),选择的复杂度为 O(n2),最好的情况下,冒泡排序的复杂度为 O(n) 和选择排序有 O(n2)