不能理解快速选择算法

Cant understand Quick Select Algorithm

本文关键字:算法 快速选择 能理解 不能      更新时间:2023-10-16

我有一个问题,理解快速选择算法。我知道它是基于快速排序算法(我很熟悉),它给你所需的结果,可能会留下数组的一部分未排序。这就是我遇到困难的地方。问题是找出数组中第二小的元素也就是

int a[4] = {1,3,5,2} ;

现在假设我们随机选择pivot,那么根据这篇文章,我们有以下条件:

  • k == pivot。那么你已经找到了第k个最小值。这是因为分区的工作方式。

  • 有k - 1个元素小于第k个元素。
  • k < pivot

  • k > pivot。第k个最小的在主元的右边。要找到它,你必须找到k-主元最小值

如果有人能解释k==pivot意味着我们已经找到了第k(在我的情况下是第二小的元素),我会很感激。如果它是k < pivot,我们是否对左侧的枢轴重复此过程?

如果k = pivot,则pivot左侧将有k-1个项。多亏了分划,每一项都小于主项。而且,由于分区,右边的每一项都大于主项。因此主元素一定是第k大的。有道理吗?

是的,当pivok == k时,你在枢轴左侧有k-1元素小于,所以你找到了数组中k-th最小的元素,即枢轴,但如果k < pivot,在数组的左侧搜索,因为pivot >第k个最小的元素,否则pivot <第k个最小的元素,所以在数组的右侧搜索以增加枢轴。
来自维基百科:

// Returns the n-th smallest element of list within left..right inclusive (i.e. n is zero-based).
  function select(list, left, right, n)
     if left = right        // If the list contains only one element
         return list[left]  // Return that element
     pivotIndex  := ...     // select a pivotIndex between left and right, e.g. left + Math.floor(Math.random() * (right - left + 1))
     pivotIndex  := partition(list, left, right, pivotIndex)
     // The pivot is in its final sorted position
     if n = pivotIndex
         return list[n]
     else if n < pivotIndex
         return select(list, left, pivotIndex - 1, n)
     else
         return select(list, pivotIndex + 1, right, n)