快速排序(三)

双路快速排序:首先将这块数据分为三个部分,左右两端分别为:左<=v,右>=v,中间为未探索的元素。

1:先从左边i开始循环,直到找到arr[i]>=v的值后结束循环,记录下此时i的值,因为此时arr[i]>v的。

2:右边j找到arr[j]<=v结束循环,记录此时j的值。

3:判断此时i和j的大小,是否数据已经检索完毕。若没有检索完,将之前记录下来的arr[i]和arr[j]互换。

此时就可以将这一串数据分别找到了左边<=v,右边>=v的部分。

template <typename T>
int  __partition_2(T arr[],int l,int r)
{
    swap(arr[l],arr[rand()%(r-l+1)+l]);
    T v =arr[l];
    // arr[l+1..i)<=v;arr(j..r]>=v
    int i=l+1,j=r;
    while(true)
    {
        while(i<=r&&arr[i]<v) i++;
        while(j>=l+1 && arr[j]>=v) j--;
        if(i>j) break;
        swap(arr[i],arr[j]);
        i++;
        j--;
    }
    swap(arr[l],arr[j]);
    return j;

}
template  <typename T>
void __quickSort2(T arr[],int l,int r)
{
    if(r-l<=15) {
        insertinonSort(arr, l, r); //在数据小到一定程度时,插入选择排序更快。即O(n)^2的时间复杂度要小于O(NlogN)
        return;
    }
    int p=__partition_2(arr,l,r);
    __quickSort2(arr,l,p-1);
    __quickSort2(arr,p+1,r);
}

template <typename T>
void quickSort2(T arr[],int n)
{
    __quickSort2(arr,0,n-1);
}

 

posted @ 2018-03-27 13:32  boht  阅读(121)  评论(0编辑  收藏  举报