• 快速排序


    快速排序


    一、简介:

    快速排序(Quicksort)是对冒泡排序的一种改进。
    它的基本思想是:

      通过一趟排序将要排序的数据分割成独立的两部分,
      其中一部分的所有数据都比另外一部分的所有数据都要小,
      然后再按此方法对这两部分数据分别进行快速排序,
      整个排序过程可以递归进行,
      以此达到整个数据变成有序序列。

    算法稳定性: 不稳定排序算法。


    二、代码示例:

    第一种,笨方法,根据基本思想,递归左右分割数组,但这样太浪费空间:

    /**
     * 快速排序
     * @param  array  $arr 数组
     * @param  boolean $asc 是否升序
     * @return array
     */
    function quick_sort($arr){
        if(!is_array($arr)){
            return [];
        }
        $len = count($arr);
        if($len <= 1){
            return $arr;
        }else if($len == 2){
            if($arr[0]>$arr[1]){
                return array($arr[1],$arr[0]);
            }else{
                return $arr;
            }
        }
        $left_arr = [];
        $right_arr = [];
        $middle_value = $arr[0];//标尺选择第一个元素
        for ($i=1; $i < $len; $i++) { 
            if($arr[$i]<$middle_value){
                $left_arr[] = $arr[$i];
            }else{
                $right_arr[] = $arr[$i];
            }
        }
        $left = quick_sort($left_arr);
        $right = quick_sort($right_arr);
        return array_merge($left,array($middle_value),$right);
    }

    第二种,精巧的方式:

    (左指针、右指针同时向中间移动,不定义新的数组,就不消耗额外的空间,使用引用传值,注意会改变原有变量)

    /**
     * 快速排序
     * @param  [type]  &$arr  数组
     * @param  integer $begin 开始位置
     * @param  [type]  $end   结束位置
     * @return [type]         null
     */
    function quick_sort(&$arr,$begin=0,$end=null){
        if(!is_array($arr)){
            return;
        }
        $len = count($arr);
        if($len <= 1){
            return;
        }
        if($end === null){
            $end = $len - 1;
        }
        if($end - $begin <= 1){
            return;
        }
        $value = $arr[$begin];//以第一个为标尺值
        $right_to_left = true;//是否从右到左
        $p1 = $begin;//左侧指针
        $p2 = $end;//右侧指针
        while($p1<$p2){
            if($right_to_left){
                //从右侧开始,每项与标尺值比较,
          //若比标尺值小,则把值放到前边,然后换循环方向,从左侧开始
                for ($i=$p2; $i>$p1; $i--) { 
                    if($arr[$i]<=$value){
                        $arr[$p1++] = $arr[$i];
                        $right_to_left = false;
                        $p2 = $i;
                        continue 2;
                    }
                }
                $p2 = $p1;
            }else{
                //从左侧开始,每项与标尺值比较,
                //若比标尺值大,则把值放到前边,然后换循环方向,从右侧开始
                for ($i=$p1; $i < $p2; $i++) { 
                    if($arr[$i]>=$value){
                        $arr[$p2--] = $arr[$i];
                        $right_to_left = true;
                        $p1 = $i;
                        continue 2;
                    }
                }
                $p1 = $p2;
            }
        }
        $arr[$p1] = $value;
        quick_sort($arr,$begin,$p1-1);
        quick_sort($arr,$p1+1,$end);
    }


  • 相关阅读:
    用 Mac 给树莓派重装系统
    Python:matplotlib 中文乱码的解决方案
    Python: 通过 pip 安装第三方包后依然不能 import
    Python: 安装 sklearn 包出现错误的解决方法
    grub2引导安装kali2.0及安装ibus拼音输入法
    2015移动安全挑战赛 第一题
    Linux kali 3.14-kali1-amd64 编译安装 wine 1.7.33
    git clone https协议问题
    常见问题
    Sieve_of_Eratosthenes
  • 原文地址:https://www.cnblogs.com/gyfluck/p/10571889.html
Copyright © 2020-2023  润新知