快速排序

·  阅读 125
快速排序

快速排序原理

  • 选择一个Pivot,将大的放置在Pivot的右边,小的放置到Pivot的左边,然后再分别对左右子数组进行相同的操作。

代码实现

function quickSort(arr, low, high){
    if(low < high){
        let index = getIndex(arr, low, high);
        
        quickSort(arr, low, index - 1);
        quickSort(arr, index + 1, high);
    }
}

function getIndex(arr, low, high){
    // 基准数据
    let tmp = arr[low];
    while(low < high){
        // 当队尾的元素大于等于基准数据时,向前挪动high指针
        while(low < high && arr[high] >= tmp){
            high--;
        }
        // 如果队尾元素小于tmp了,需要将其赋值给low
        arr[low] = arr[high];
        
        
        // 当队首元素小于等于tmp时,向前挪动low指针
        while(low < high && arr[low] <= tmp){
            low++;
        }
        // 当队首元素大于tmp时,需要将其赋值给high
        arr[high] = arr[low];
    }
    
    // 跳出循环时low和high相等,此时的low或high就是tmp的正确索引位置
    // 由原理部分可以很清楚的知道low位置的值并不是tmp,所以需要将tmp赋值给arr[low]
    arr[low] = tmp;
    
    return low;
}
复制代码

第二种实现方案

function quick(arr) {
    if (arr.length <= 1) return arr;
    const len = arr.length;
    const index = Math.floor(len >> 1);
    const pivot = arr.splice(index, 1)[0];
    const left = [];
    const right = [];

    for (let i = 0; i < len; i++) {
      if (arr[i] > pivot) {
        right.push(arr[i])
      } else if (arr[i] <= pivot) {
        left.push(arr[i])
      }
    }
    return quick(left).concat([pivot], quick(right))
  }
复制代码

主要步骤

  • 先从队尾开始向前扫描且当low < high时,如果arr[high] > tmp,则high–,但如果arr[high] < tmp,则将high的值赋值给low,即arr[low] = arr[high],同时要转换数组扫描的方式,即需要从队首开始向队尾进行扫描了.
  • 同理,当从队首开始向队尾进行扫描时,如果arr[low] < tmp,则low++,但如果arr[low] > tmp了,则就需要将low位置的值赋值给high位置,即arr[low] = arr[high],同时将数组扫描方式换为由队尾向队首进行扫描.
  • 不断重复前两步,直到low>=high时(其实是low=high),low或high的位置就是该基准数据在数组中的正确索引位置.

算法效率

  • 时间复杂度:平均时间复杂度O(nlogn)
  • 空间复杂度:最好空间复杂度为O(logn),最坏空间复杂度为O(n)
分类:
前端
标签:
分类:
前端
标签:
收藏成功!
已添加到「」, 点击更改