排序算法(五):快速排序

基本思想

在数组中选取一个数作为基准值,进行一个partition过程,将小于该数的放在左边,大于的放在右边,等于的放在中间,再对左右分别进行该操作。

时间复杂度:每次partition可以将一个数字位置确定,将数组划分为两部分,因此想要有序,理想情况每次刚好两边大小一样,则一共需要logn次partition过程,每次partition过程时间复杂度O(n),因此最好时间复杂度O(nlogn),平均时间复杂度O(nlogn),但是时间复杂度和选取的基准值有关,如果选取的基准值不好,则每次划分的区间很不均匀,会影响时间复杂度,极限情况每次选取的基准值为最大值或者最小值,则一共需要n次partition过程,时间复杂度退化为O(N^2),为了解决这个问题,引入随机快排,即选取基准值时选择数组一个随机值,时间复杂度的计算变成概率问题,长期期望下时间复杂度为O(nlogn)

空间复杂度:O(1)

算法描述

  • 选取数组末尾值作为基准值进行partition过程
  • 一次partition过程后,数组划分为两部分,两部分分别进行partition过程
  • logn次partition过程后,数组有序

代码实现

package cn.lzx.sort;

/**
 *@ClassNameQuickSort
 *@Description  快排
 *@Author lzx
 *@Date2019/10/28 13:16
 *@Version V1.0
 **/
public class QuickSort {


    private static void quickSort(int[] arr){
        if (arr == null || arr.length < 2){
            return;
        }
        quickSort(arr,0,arr.length-1);
    }

    private static void quickSort(int[] arr,int left,int right){
        if (left < right){
            int[] partition = partition(arr, left, right,arr[right]);
            quickSort(arr,left,partition[0]-1);
            quickSort(arr,partition[1]+1,right);
        }
    }


    /**
     * 将数组的某一区域划分为小于num和大于num的两部分区域 返回等于区域的左右下标
     * @param arr  数组
     * @param left  数组左边界
     * @param right  数组右边界
     * @param num  比较数值
     * @return  等于区域的左右下标
     */
    private static int[] partition(int[] arr,int left,int right,int num){

        //小于区域
        int less = left - 1;
        //大于区域
        int more = right + 1;
        //当前下标
        int cur = left;
        while(cur < more){
            if (arr[cur] < num){
                swap(arr,++less,cur++);
            }else if (arr[cur] > num){
                swap(arr,--more,cur);
            }else {
                cur++;
            }
        }
        return new int[]{less + 1,more - 1};
    }


    private static void swap(int[] arr, int i, int j) {
        int tmp = arr[i];
        arr[i] = arr[j];
        arr[j] = tmp;
    }

    private static void print(int[] arr) {
        StringBuilder res = new StringBuilder();
        for (int i = 0; i < arr.length; i++) {
            res.append(arr[i]).append(" ");
        }
        System.out.println(res.toString());
    }


    public static void main(String[] args) {
        int[] arr = new int[]{-8,21,8,15,4,0,2,9,-5,17};
        quickSort(arr);
        print(arr);
    }
}

 

 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值