Partition方法

/**
 * partition()方法:在基准元素左边的元素都小于基准元素,在基准元素右边的元素都大于等于基准元素。
 *
 * 可以使用partition()方法解决以下常见的问题:
 *
 *  1)查找数组中出现次数超过数组长度一半的元素。
 *      eg:MoreThanHalfSize类中的getElementOfMoreThanHalfSizeByPartition方法。
 *  2)查找数组中最小的(或最大的)k个数 或 查找数组中第k小(或第k大)的数。
 *
 * 优点:时间复杂度为O(n)
 *
 * 缺点:改变了原数组中元素的位置。
 *
 */
public class Partition {


    /**
     * 获取基准元素的下标。
     *
     * @param array 待排序的数组
     * @param left  起点索引
     * @param right 终点索引
     * @return
     */
    public static int partition(int[] array, int left, int right) {

        // 选取数组的头元素作为基准元素
        int pivotPosition = left;           
        int pivot = array[pivotPosition];

        /**
         * 循环结束后:
         *      pivotPosition后面的元素都大于等于基准元素pivot
         *      pivotPosition前面的元素(包括pivotPosition指向的元素)除了基准元素pivot外,其它元素都小于基准元素pivot
         */
        for (int i = pivotPosition + 1; i <= right; i++) { // i表示当前元素的索引

            if (array[i] < pivot) {

                swap(array, pivotPosition, i);
                pivotPosition++;

            }
        }

        /**
         * 目的:
         *      将pivotPosition指向基准元素pivot,并且返回pivotPosition,以确定递归函数quickSort()中left参数与right参数的值
         * 实现:
         *      交换基准元素与pivotPosition当前指向元素的位置。
         */
        if (pivotPosition != left) {
            array[left] = array[pivotPosition];
            array[pivotPosition] = pivot;
        }

        return pivotPosition;
    }


    /**
     * 将数组中下标为indexOfK的元素设为基准元素,即小于基准元素的放在左边,大于或等于基准元素的放在右边。
     *
     * @param array
     * @param left
     * @param right
     * @param indexOfK  基准元素的下标
     */
    public static void makePivotIndexEqualsK(int[] array, int left, int right, int indexOfK) {

        // 基准元素的下标
        int pivotIndex = Partition.partition(array, left, right);

        while (pivotIndex != indexOfK) {

            if (pivotIndex > indexOfK) {
                right = pivotIndex - 1;
            } else {
                left = pivotIndex + 1;
            }
            pivotIndex = Partition.partition(array, left, right);
        }

    }


    /**
     * 数组中,交换两个元素的位置
     */
    private static void swap(int[] array, int i, int j) {
        if (i != j) {
            int temp = array[i];
            array[i] = array[j];
            array[j] = temp;
        }
    }

    public static void print(int i) {
        System.out.print(i + " ");
    }

}

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值