算法初探LeetCode-排序数组

67 阅读2分钟

LeetCode912-排序数组

给你一个整数数组 nums,请你将该数组升序排列。 示例 1:

输入: nums = [5,2,3,1]
输出: [1,2,3,5]

示例 2:

输入: nums = [5,1,1,2,0,0]
输出: [0,0,1,1,2,5]

提示:

  • 1<=nums.length<=51041 <= nums.length <= 5 * 10^4
  • 5104<=nums[i]<=5104-5 * 10^4 <= nums[i] <= 5 * 10^4

思路分析

快排有较好的性能,其思想是选定数组中一个值为分界点,将数组拆分为<分界点值的元素数组、>分界点值的元素数组、分界点值组成的数组,显然如果左右数组有序,整体排序可以直接得到。

使用暴力法时可以直接创建三个数组,遍历原数组将<、=、>分界点的值放入对应数组中;

也可以使用两个数组,分别存储≤,>分界点的元素,此时需要每次去除一个分界点不参与下次排序,防止死循环

用快速排序的非递归形式,用俩个移动下标l和r来分别比较基准数,下标分别存放在栈里面,在用一个方法来调用排序得出一个中下标之后,进行分左右区间,判断是否符合分区的最小个数,成功把下标存放在栈里面。

1.用栈集合存放左右下标 2.用一个方法来得出中下标位置 3.判断中下标的左右区间 4.回到步骤1循环这几步操作,知道栈为空,则排序完成。

算法代码

public int[] sortArray(int[] nums) {
    int start = 0;
    int end = nums.length - 1;
    Stack < Integer > stack = new Stack < > ();
    if (start < end) {
        stack.push(end);
        stack.push(start);
        while (!stack.isEmpty()) {
            int l = stack.pop();
            int r = stack.pop();
            int index = partition(nums, l, r);
            if (l < index - 1) {
                stack.push(index - 1);
                stack.push(l);
            }
            if (r > index + 1) {
                stack.push(r);
                stack.push(index + 1);
            }
        }
    }
    return nums;
}

private int partition(int[] a, int start, int end) {
    int point = a[start];
    while (start < end) {
        while (start < end && a[end] >= point)
            end--;
        a[start] = a[end];
        while (start < end && a[start] <= point)
            start++;
        a[end] = a[start];
    }
    a[start] = point;
    return start;
}

结果详情

Snipaste_2023-05-01_23-31-15.png

算法复杂度

  • 空间复杂度:O(1)O(1)
  • 时间复杂度:O(n)O(n)

掘金(JUEJIN)一起进步,一起成长!