快速排序算法-Quick Sort

算法思想

快速排序使用了分治思想,即:

  • 分解:数组以一个随机元素K为分割数,被划分为两个部分,左边部分的每一个元素都小于等于K,右边部分的每一个元素都大于等于K。

  • 解决:通过递归调用函数,对左边和右边进行排序。

  • 合并:因为在原空间进行排序,所以不需要合并。

具体来分析数组分解的动作:
以数组arr[] = {6,4,7,2,8};为例,用i和j标记数组的起始位置和末尾位置,即i=0,j=4。选6为分割数,即k=6。然后进行下面步骤:

  1. 将j往左移动,直到找到小于等于分割数(6)的元素(2),然后将此时i(即6)的位置赋值为2。
    这里写图片描述
  2. 将i往右移动,直到找到大于等于分割数(6)的元素(7),然后将此时j(即上图红色2)的位置
    这里写图片描述
  3. 重复1,2步直到i和j重合,此时将分割值(6)放到i的位置,分割值所有左边的元素小于等于它,右边的元素都大于等于它。
    这里写图片描述

算法实现

将上述过程用代码实现:

int partition(int *arr,int lef,int rigt)
{
    int i = lef,j = rigt;
    int k = arr[i];

    while(i < j)
    {
        while(i<j && arr[j]>=k)
            j--;
        if(i < j)
            arr[i++] = arr[j];

        while(i<j && arr[i]<k)
            i++;
        if(i < j)
            arr[j--] = arr[i];

        arr[i] = k;

    }
    return i;
}

再递归排序:

int qksort(int *arr,int lef,int rigt)
{
    if(lef < rigt)
    {
        int n = partition(arr,lef,rigt);
        qksort(arr,lef,n-1);//左边排序
        qksort(arr,n+1,rigt);//右边排序

        //左边和右边排序的另一种写法
        //qksort(arr,lef,n);
        //lef = n+1;
    }
    return 0;
}

应用 :

int main()
{
    int i;
    int arr[5] = {6,4,7,2,8};

    qksort(arr,0,4);

    for(i=0; i<5; i++)
        printf("%d ", arr[i]);
    return 0;
}

结果:

这里写图片描述

算法分析

快速排序在最坏的情况下时间为O(n^2) ,最理想的时间为O(n*lgn),虽然它在最坏的情况下并不理想,但它的平均性能好,并且不需要额外开辟内存空间,所以其应用也很广泛。

算法优化

在运气很差的情况下选到的分割数是最大值或者最小值,其时间为O(n^2),随机选择能够有效的被分割的数据的不平衡。我们还可以设置一个保底机制,即选择三个随机元素,取中间值作为分割数,以保持算法的整体性。

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值