2.排序算法

92 阅读1分钟

1 冒泡排序

时间复杂度O(n^2)

function bubbleSort(arr){
  for(let i=0; i<arr.length-1; i++){ // 循环len-1轮
    for(let j=0; j<arr.length-1-i; j++){ // 比较到最新的已排序好的项
      if(arr[j] > arr[j+1]) [arr[j], arr[j+1]] = [arr[j+1], arr[j]] 
    }
  }
}

2 选择排序

时间复杂度O(n^2)

function selectionSort(arr){
  let minIdx;
  for(let i=0; i<arr.length-1; i++){ // 循环len-1轮
    minIdx = i // 每轮循环选出当前最小的项放前面
    for(let j=i+1; j<arr.length; j++){
      if(arr[j] < arr[minIdx]) minIdx = j
    }
    [arr[i], arr[minIdx]] = [arr[minIdx], arr[i]]
  } 
}

3 插入排序

时间复杂度O(n^2)

function insertSort(arr){
  let temp,j;
  for(let i=1,j=i; i<arr.length;i++){ // 默认第一个是已排序好的
    temp = arr[j]
    while(j>0&&arr[j-1]>temp){
      [arr[j-1], arr[j]] = [arr[j], arr[j-1]]
      j--
    }
  }
}

4 归并排序

时间复杂度O(nlogn),采用分而治之的思想,先分后排

function mergeSort(arr){
  let len = arr.length
  if(len===1) return arr // 基准
  
  let mid = Math.floor(len/2)
  let left = arr.splice(0,mid)
  let right = arr.splice(mid)
  
  return arr = merge(mergeSort(left),mergeSort(right)) // 入执行栈
}

function merge(left,right){
  let l = 0
  let lMax = l.length-1
  let r = 0 
  let rMax = r.length-1
  let res = []
  
  while(l<=lMax && r<=rMax){
    if(left[l]<right[r]) res.push(left[l++])
    else res.push(right[r++])
  }
  
  while(l<=lMax) res.push(left[l++])
  while(r<=rMax) res.push(right[r++])
  
  return res
}

5 快速排序

时间复杂度O(nlogn),同样采用分而治之的思想,先排后分

// 简版
function quickSort(arr){
  let len = arr.length
  if(len===1) return arr // 基准
  
  let mid = arr.splice(Math.floor(len/2),1)[0]
  let left = []
  let right = []
  arr.forEach(item=>{
    if(item<=mid) left.push(item)
    else right.push(item)
  })
  return arr = [...quickSort(left), mid, ...quickSort(right)]
}

// 双指针法
funtion quickSort(arr,left=0,right=arr.length){
  let len = arr.length
  if(len===1) return arr // 基准
  
  // 抽象调用层
  let mid = partition(arr,left,right)
  if(left<mid-1) quickSort(arr,left,mid-1)
  if(right>mid) quickSort(arr,mid,right)
}

function partition(arr,l,r){ // 实际执行层
  let pivot = arr[Math.floor((r+l)/2)]
  while(l<r){
    while(arr[l]<pivot) l++  // 找出不小于pivot的项
    while(arr[r]>pivot) r-- // 找出不大于pivot的项
    if(l<r){
      [arr[l], arr[r]] = [arr[r], arr[l]]
      l++
      r--
    }
  }
  return l
}