【问题标题】:QuickSort for sorting part Mergesort?用于排序部分合并排序的快速排序?
【发布时间】:2015-06-28 04:39:27
【问题描述】:

问题:Mergesort 将一个数字列表分成两半,并在这两部分上递归调用自身。相反,您可以在左半边执行快速排序并在右半边执行合并排序吗?如果是,请通过显示每个步骤来显示它将如何对以下数字列表进行排序。如果不是,请解释为什么不能。

我应该使用合并排序对数字列表进行排序。使用快速排序将左半部分排序在哪里?

我想通了。 答:是的,我们可以

  1. 使用归并排序对数组的右半部分进行排序。
  2. 使用快速排序对左半部分进行排序。
  3. 使用merge_sort的合并函数合并2。

【问题讨论】:

  • 假设您计划在完成后合并“左半部分”和“右半部分”,您使用哪种排序算法有什么关系(您是否尝试使用就地快速排序来节省空间?)。并且快速排序和合并排序都可以在 C 中轻松实现,只需使用基指针和序列长度作为参数。创造性的指针算法会以最小的努力消除一个索引(低索引)。我完全有可能误解了你提出的问题,如果是这样,也许澄清一下你实际上试图做什么?
  • 我更新了问题。我也从你的回复中发现,我可以在对它们进行排序后合并两半。谢谢。

标签: sorting language-agnostic quicksort mergesort


【解决方案1】:

不,你不能这样做。至少如果您仍想将其称为“合并排序”。归并排序和快速排序最根本的区别在于前者是一种稳定的算法,即等序元素在排序后保持其相对位置不变。这在许多情况下都很重要。 如果您使用快速排序对后半部分进行排序,则相等元素的相对位置可以(并且很可能会)改变。结果集不会保持稳定性,因此仍不能视为归并排序。

顺便说一句,关于用作合并排序最后一步的插入排序,先前的答案是正确的。当元素数量很少时,最有效的合并排序实现将使用诸如插入排序之类的东西。插入排序也很稳定,这就是为什么它可以在不破坏合并排序稳定性的情况下完成。

【讨论】:

    【解决方案2】:

    是的,您可以这样做。归并排序背后的基本思想如下:

    1. 将数组拆分为两个(或更多)部分。
    2. 独立排序每一件。
    3. 应用合并步骤将已排序的部分合并为一个整体排序列表。

    从正确性的角度来看,如何对第 (2) 部分中生成的列表进行排序实际上并不重要。重要的是这些列表得到排序。合并排序的典型实现通过递归地将自身应用于左右两半来执行步骤 (2),但没有根本原因必须这样做。 (事实上​​,在某些优化的归并排序版本中,您特别这样做,而是在数组变得足够小时时切换到插入排序之类的算法。

    在您的情况下,您是正确的,在左侧使用快速排序并在右侧使用合并排序仍然会产生排序序列。但是,它的工作方式看起来与您所描述的完全不同。最终会发生这样的事情:数组的前半部分会被快速排序(因为你对左半部分进行快速排序),然后你会递归地对右半部分进行排序。 that 的前半部分会被快速排序,然后你会递归地对右半部分进行排序。 的前半部分会被快速排序,等等。总的来说,这看起来像这样:

    • 您快速排序数组的前半部分,然后是剩余部分的前半部分,然后是剩余部分的前半部分,依此类推,直到没有剩余元素为止。
    • 然后,从左到右,将最后两个元素合并在一起,然后是最后四个,然后是最后八个,依此类推。

    这将是一个看起来很酷的排序,但手动操作会非常痛苦。您最好编写一个程序来执行此操作并显示所有中间步骤。 :-)

    【讨论】:

      猜你喜欢
      • 2015-05-26
      • 2021-06-06
      • 2010-10-04
      • 1970-01-01
      • 1970-01-01
      • 2014-01-08
      • 1970-01-01
      • 2013-12-08
      • 1970-01-01
      相关资源
      最近更新 更多