美文网首页
快速排序--阮一峰老师的方法究竟存在什么争议?

快速排序--阮一峰老师的方法究竟存在什么争议?

作者: 宋乐怡 | 来源:发表于2020-02-25 11:34 被阅读0次

    R:

    var quickSort = function(arr) {
     
      if (arr.length <= 1) { return arr; }
     
      var pivotIndex = Math.floor(arr.length / 2);
     
      var pivot = arr.splice(pivotIndex, 1)[0];
     
      var left = [];
     
      var right = [];
     
      for (var i = 0; i < arr.length; i++){
     
        if (arr[i] < pivot) {
     
          left.push(arr[i]);
     
        } else {
     
          right.push(arr[i]);
     
        }
     
      }
     
      return quickSort(left).concat([pivot], quickSort(right));
     
    };
    
    

    思路:
    1.选择中间元素作为基数。
    2.新开辟两块内存空间,分别存放比基数小的值和比基数大的值。
    3.递归左右数组,拼接中间值

    争议:
    1.取中间值的方式不直观,下标法是数组效率最高的方式, 调用splice函数是额外的开销。
    2.新开辟的两个数组是不必要的内存开销。

    优化:
    从存疑的两个方向来优化代码
    1.key的位置究竟是哪,其实并不重要,所以就取第一个就ok。
    2.原地交换,不开辟新空间。

    var arr=[5,7,2,9,3,8,4,7,1];
    // 每次选择最左边的数作为基数
    function quickSort(arr){
      if (arr.length<2) { return arr; }
      // 定义左指针
      var left=0;
      // 定义右指针
      var right=arr.length-1;
      //开启每一轮的排序
      while(left<right){
        // 寻找右边比arr[0]小的数的下标
        while(arr[right]>=arr[0] && left<right){
          right=right-1;
        }
        // 寻找左边比arr[0]大的数的下标
        while(arr[left]<=arr[0] && left<right){
          left++;
        }
        //当左边指针与右边指针相遇后,交换arr[0]与当前两个指针所在的元素
        if (right==left) {
          let mid=arr[right];
          arr[right]=arr[0];
          arr[0]=mid;
          break;
        }
        // 当左指针小于右指针的位置,交换两个指针当前位置的元素
        let tem=arr[right];
        arr[right]=arr[left];
        arr[left]=tem;
      }
      //递归实现
      return quickSort(arr.slice(0,left)).concat(arr.slice(left,right+1)).concat(quickSort(arr.slice(right+1)));
    }
    //对数组进行排序
    console.log(quickSort(arr));
    

    相关文章

      网友评论

          本文标题:快速排序--阮一峰老师的方法究竟存在什么争议?

          本文链接:https://www.haomeiwen.com/subject/vlmzqhtx.html