《github一天一道算法题》:快速排序和随机快速排序

看书、思考、写代码!!!

/*********************************
 * copyright@hustyangju
 * blog: http://blog.csdn.net/hustyangju
 * 题目:快速排序和随机快速排序
 * 思路:采用分治+原址排序,分裂函数将区间分为三个子区间:<=主元、主元和>主元区间,再在主元旁边的两个子区间递归调用排序
 *      分裂函数一般将区间最后一个元素作为比较的主元,随机快排则随机选取区间内的一个元素交换到末尾作为主元
 * 空间复杂度:原址排序的空间复杂度可以视为0
 * 快排时间复杂度:最坏的情况下,即全部逆序,为0(n*n),期望时间复杂度为O(n lgn),实际情况下系数常量较小,效果较好
 * 随机快排时间复杂度:出现最坏的情况的可能性较低,数据量越大,时间复杂度越好于前一种快排,期望也为O(n lgn),实际情况下系数常量较小,效果较好
*/
#include <iostream>
#include <algorithm>

using namespace std;

class quick_sort_class
{
  public:
    quick_sort_class(int *a, int n):p_array(a), n_array(n){}//构造函数
    ~quick_sort_class();//析构函数
    void quick_sort(int i, int j);//快排接口
    void rand_quick_sort(int i, int j);//随机快排接口
    void print();//输出接口
  protected:
    int partition(int p, int r);//快排分裂函数,选取最后一个元素作为主元
    int rand_partition(int p, int r);//随机快排分裂函数,随机选取区间内的一个元素作为主元,移到最后一位
  private:
    int *p_array;
    int n_array;

};

quick_sort_class::~quick_sort_class()
{
}

//快排分裂函数,将区间元素分为:<=主元、主元和>主元 的三个区间,返回主元的位置
int quick_sort_class::partition(int p, int r)
{
    int x = p_array[r];
    int i = p-1;
    for(int j=p;j<r;++j)
    {
        if(p_array[j]<=x)
        {
            ++i;
            swap(p_array[i], p_array[j]);
        }
    }
    swap(p_array[i+1], p_array[r]);
    return i+1;
}

//随机快排的分裂函数,关键在于主元的选取,适合大量随机数的快速排序
int quick_sort_class::rand_partition(int p, int r)
{
    int a=p+rand()%(r-p+1);
    swap(p_array[a],p_array[r]);
    return partition(p,r);
}

//递归法、原址快速排序,采用3段分治策略,因为是原址,没有归并的必要
void quick_sort_class::quick_sort(int i, int j)
{
    if(i<j)
    {
        int q = partition(i, j);
        quick_sort(i, q-1);
        quick_sort(q+1, j);
    }
}

//递归法、原址快速排序,采用3段分治策略,因为是原址,没有归并的必要,调用随机分裂函数
void quick_sort_class::rand_quick_sort(int i, int j)
{
    if(i<j)
    {
        int q = rand_partition(i, j);
        quick_sort(i, q-1);
        quick_sort(q+1, j);
    }
}
//输出接口
void quick_sort_class::print()
{
    for(int i=0;i<n_array;++i)
        cout<<p_array[i]<<" ";
    cout<<endl;
}

int main()
{
    int array[10] = {8, 4, 7, 15, 10, 84, 23, 19, 3, 11};
    quick_sort_class myQuickSort(array, 10);
    cout<<"origin array:"<<endl;
    myQuickSort.print();
    cout<<"quick sort:"<<endl;
    myQuickSort.quick_sort(0, 9);
    myQuickSort.print();
    cout<<"******************"<<endl;
    int array1[10] = {8, 4, 7, 15, 10, 84, 23, 19, 3, 11};
    quick_sort_class myQuickSort1(array1, 10);
    cout<<"origin array:"<<endl;
    myQuickSort1.print();
    cout<<"rand quick sort:"<<endl;
    myQuickSort1.rand_quick_sort(0, 9);
    myQuickSort1.print();
}
测试结果:



  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值