zoukankan      html  css  js  c++  java
  • 快排算法的实现

    先来说网上流行最多的实现,用两个指针,一个从前往后,一个从后往前。直接上代码,如下。

     1 package com.jeaven;
     2 
     3 public class Solution2 {
     4     public void quick_sort(int[] arr, int begin, int end) {
     5         if(begin < end) {
     6             int mid = partition(arr, begin, end);
     7             quick_sort(arr, begin, mid-1);
     8             quick_sort(arr, mid+1, end);
     9         }
    10     }
    11     
    12     
    13     /* 双向指针的快排思路
    14      * 前一个指针指向开始元素begin,第二个指针指向数组倒数第二个end-1,最后一个元素为轴pivot
    15      *当arr[i] > pivot时,交换arr[i]和arr[j]然后 j=j-1
    16      *当arr[i] < pivot时,就i++
    17      *最终当i和j重合的时候相遇,再将轴归位返回轴的位置,注意下标即可
    18     */
    19     public int partition(int[] arr, int begin, int end) {
    20         int pivot = arr[end];
    21         int i = begin;
    22         int j = end - 1;
    23         while(i < j) {
    24             if(arr[i] > pivot) {
    25                 int temp = arr[j]; 
    26                 arr[j] = arr[i];
    27                 arr[i] = temp;
    28                 j--;
    29             } else {
    30                 i++;
    31             }
    32         }
    33         int temp = arr[j+1];
    34         arr[j+1] = arr[end];
    35         arr[end] = temp;
    36         return j+1;
    37     }
    38     
    39     public static void main(String[] args) {
    40         int[] arr = {1,4,2,3,5};
    41         new Solution2().quick_sort(arr, 0, arr.length-1);
    42         for(int c : arr) {
    43             System.out.print(c + " ");
    44         }
    45     }
    46 }

    再来说说我最喜欢的风格,也是算法导论上的快排实现方法,两个指针从同一边开始,算法导论的思路很清晰,还给出了完整的理论推导,不变性的证明,有兴趣的可以去看看算法道路的快排章节。

    下面是算法导论关于快排的实现思路,如下:

     然后我给出java版本的快排实现:

     1 package com.jeaven;
     2 
     3 public class Solution3 {
     4     public void quick_sort(int[] arr, int begin, int end) {
     5         if(begin < end) {
     6             int mid = partition(arr, begin, end);
     7             quick_sort(arr, begin, mid-1);
     8             quick_sort(arr, mid+1, end);
     9         }
    10     }
    11     
    12     public int partition(int[] arr, int begin, int end) {
    13         int pivot = arr[end];
    14         int i = begin - 1;
    15         for(int j = begin; j < end; j++) {
    16             if(arr[j] < pivot) {
    17                 i++;
    18                 int temp = arr[j];
    19                 arr[j] = arr[i];
    20                 arr[i] = temp;
    21             }
    22         }
    23         int temp = arr[i+1];
    24         arr[i+1] = arr[end];
    25         arr[end] = temp;
    26         return i+1;
    27     }
    28     
    29     public static void main(String[] args) {
    30         int[] arr = {1,4,2,3,5};
    31         new Solution3().quick_sort(arr, 0, arr.length-1);
    32         for(int c : arr) {
    33             System.out.print(c + " ");
    34         }
    35     }
    36 }

    说明:我喜欢选最后一个元素为轴pivot,当然可以选取数组任意位置为轴,即使分的恨不均匀,但是可以证明除了极端情况,时间复杂度仍然为O(nlgn)。如果选取其他位置作为轴,代码实现的时候可以先将轴和最后一个元素交换位置,这样就可以看成是最后一个位置是轴,就可以很容易实现。

  • 相关阅读:
    python匿名函数与bif-第五天
    python函数-第四天
    python元组与序列-第三天
    idea激活码最新获取方法(idea2020激活码汇总)
    hbase shell操作之scan+filter
    hbase过滤及查看数据知识点-day02
    Hbase基本知识点总结
    Python列表-一个打了激素的数组(3)
    SQL 随记
    数据库链接失败,报用用户密码错误
  • 原文地址:https://www.cnblogs.com/jeavenwong/p/11712260.html
Copyright © 2011-2022 走看看