zoukankan      html  css  js  c++  java
  • 快速排序

    一---基本思想

    先给定一个数组{-3,2,0,5,-4,1},设定一个标杆,假设就是中间值0,然后一头一尾两个指针,去对数组进行重新排序,排序的结果为中间值0的左边的数全部小于0,而标杆0的右边的数全部大于0。此时数组为{-3,-4,0,5,2,1}。然后再用相同的思想对0左边的数进行递归得{-4,-3,0,5,2,1},对0右边的数进行递归得{-4,-3,0,1,2,5}。

    二---图解

    三---代码

     1 public class QuickSort {
     2     public static void main(String[] args) {
     3         int[] arr = {-3,2,0,5,-4,1};
     4         quickSort(arr, 0, arr.length - 1);
     5         System.out.println(Arrays.toString(arr));
     6     }
     7     public static void quickSort(int[] arr, int left, int right) {
     8        int l = left;
     9        int r = right;
    10         int temp = 0;
    11        int pivot = arr[(left + right) / 2];
    12        while(l < r) { // 只要l < r,说明还没有排完
    13            while(arr[l] < pivot) { // 找出左边大于等于pivot的数
    14                l++;
    15            }
    16            while(arr[r] > pivot) { // 找出右边小于等于pivot的数
    17                r--;
    18            }
    19            // 如果l == r,说明左边的数都是小于中轴值,右边的数都是大于中轴值,无需交换,退出。
    20            if(l == r) {
    21                break;
    22            }
    23            // 如果上面的语句没有执行,说明左边有比中轴值小的,右边有比中轴值大的,交换。
    24            temp = arr[l];
    25            arr[l] = arr[r];
    26            arr[r] = temp;
    27           
    28        }
    29         // 上面循环完成,代表我们已经按照中轴值左边全是小于等于中轴值,右边全是大于等于中轴值的规则排序好了
    30         // 首先判断上面排序完成后l和r是否相等,如果相等,要错开,否则会进行栈溢出
    31         if(l == r) {
    32             l++;
    33             r--;
    34         }
    35         // 左边递归排序
    36         if(left < r) { // 错开之后r是在左边的,所以这里就是r。
    37             quickSort(arr, left, r);
    38         }
    39         // 左边部分排好了,接下来进行右边
    40         if(right > l) { // 错开之后l是在左边的,所以这里就是l。
    41             quickSort(arr, l, right);
    42         }
    43     }

    四---出现问题

    上面的代码其实是有瑕疵的,思考这样一个数组

    {-4,2,0,0,7}  

    程序报错:

    改进代码,红色部分即为优化。

     1 public static void quickSort(int[] arr, int left, int right) {
     2        int l = left;
     3        int r = right;
     4         int temp = 0;
     5        int pivot = arr[(left + right) / 2];
     6        while(l < r) { // 只要l < r,说明还没有排完
     7            while(arr[l] < pivot) { // 找出左边大于等于pivot的数
     8                l++;
     9            }
    10            while(arr[r] > pivot) { // 找出右边小于等于pivot的数
    11                r--;
    12            }
    13            // 如果l == r,说明左边的数都是小于中轴值,右边的数都是大于中轴值,无需交换,退出。
    14            if(l == r) {
    15                break;
    16            }
    17            // 如果上面的语句没有执行,说明左边有比中轴值小的,右边有比中轴值大的,交换。
    18            temp = arr[l];
    19            arr[l] = arr[r];
    20            arr[r] = temp;
    21            // 交换完成,现在判断左边或右边的数是否和中轴值相同,如果相同,要进行前进或者后退,防止进入死循环。
    22            if(arr[l] == pivot) {
    23                r--;
    24            }
    25            if(arr[r] == pivot) {
    26                l++;
    27            }
    28 
    29        }
    30         // 上面循环完成,代表我们已经按照中轴值左边全是小于等于中轴值,右边全是大于等于中轴值的规则排序好了
    31         // 首先判断上面排序完成后l和r是否相等,如果相等,要错开,否则会进行栈溢出
    32         if(l == r) {
    33             l++;
    34             r--;
    35         }
    36         // 左边递归排序
    37         if(left < r) { // 错开之后r是在左边的,所以这里就是r。
    38             quickSort(arr, left, r);
    39         }
    40         // 左边部分排好了,接下来进行右边
    41         if(right > l) { // 错开之后l是在左边的,所以这里就是l。
    42             quickSort(arr, l, right);
    43         }
    44     }
  • 相关阅读:
    有点忙啊
    什么是协程
    HDU 1110 Equipment Box (判断一个大矩形里面能不能放小矩形)
    HDU 1155 Bungee Jumping(物理题,动能公式,弹性势能公式,重力势能公式)
    HDU 1210 Eddy's 洗牌问题(找规律,数学)
    HDU1214 圆桌会议(找规律,数学)
    HDU1215 七夕节(模拟 数学)
    HDU 1216 Assistance Required(暴力打表)
    HDU 1220 Cube(数学,找规律)
    HDU 1221 Rectangle and Circle(判断圆和矩形是不是相交)
  • 原文地址:https://www.cnblogs.com/YXBLOGXYY/p/14476905.html
Copyright © 2011-2022 走看看