排序|快速排序的简单实现

快排本质是分治算法,其大致流程是如下:

    public void sort(int[] arr, int l, int r) {
        if (l >= r) return;//递归终止判定

        int mid = parSort(arr, l, r);//对mid数进行排序
        sort(arr, l, mid - 1);//左递归
        sort(arr, mid + 1, r);//右递归
    }

大框架是这样的,难点在于如何将目标数组分成两个。

很多教程里面讲到,这个函数需要把数组分成一边大于某数x,另一边小于x。

其实漏掉了一个重要的东西,就是x的位置在分完之后代表着什么,有什么意义?

其实很简单,把比x小的数都放到x的左边,把x数大的数都放到x的右边,此时x在数组的下标为i,这个i其实和数组排序后x所在的位置是一样的。也就是说这个分组操作之后,就将x的位置排好了。而且也将数组更加的有序化了。


至于如何分组,可以使用一种朴素的实现方式,那就是直接创建两个数组a与b,用以存储大于等于x的数和小于x的数。至于x,不放入数组中,或者放入a中最末尾。最后将两个数组中的数覆盖原始的arr[l,r]。

代码见下:

    public void sort(int[] arr) {
        sort(arr, 0, arr.length - 1);
    }

    /*快排利用到了递归,递归要做的工作是把关键数两边的数安排好*/
    public void sort(int[] arr, int l, int r) {
        if (l >= r) {
            return;
        }
        int mid = parSort(arr, l, r);
        sort(arr, l, mid - 1);
        sort(arr, mid + 1, r);
    }

    private int parSort(int[] arr, int l, int r) {
        int mid = l + r >> 1;

        int com = arr[mid];

        int[] tmp1 = new int[r - l + 1];
        int[] tmp2 = new int[r - l + 1];
        int cnt1 = 0;
        int cnt2 = 0;
        for (int i = l; i < r + 1; i++) {
            if (i != mid) {//比较数不放进去
                if (arr[i] <= com) {
                    tmp1[cnt1] = arr[i];
                    cnt1++;
                } else {
                    tmp2[cnt2] = arr[i];
                    cnt2++;
                }
            }
        }
        int start = l;
        for (int i = 0; i < cnt1; i++) {
            arr[start] = tmp1[i];
            start++;
        }
        arr[start] = com;
        int res = start;
        start++;
        if (cnt2 > 0) {
            for (int i = 0; i < cnt2; i++) {
                arr[start] = tmp2[i];
                start++;
            }
        }
        return res;
    }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值