js算法基础三 桶排序和基数排序

40 阅读1分钟

桶排序

桶排序是指,将数组的每个元素,根据他除以某个固定数后,向下取整的值为角标,存储在数组中的一种排序方式,和计数排序一样,通过数组的有序性进行排序,这样会得到一个二维数组,只需要将这个二维数组中的数排序,再将整个二维数组转为一维即可

代码实现

    // 桶排序
    function bucketSort(arr, bucketRange = 3) {
      const [min, max] = getMinMax(arr)
      const bucketCount = Math.floor((max - min) / bucketRange) + 1

      // 创建桶
      const buckets = []
      for(let i = 0; i < bucketCount; i++) {
        buckets.push([])
      }
      // 将数据存入他应该在的桶中
      // (item - min) / bucketRange 是让min 到 (min +3)成为一个桶,在这个区间内所有元素都被存入这个桶中
      // 以此内推 (min +3) 到 (min +6) 也是一个桶,可知桶是有序的
      // 每个桶存储的 值的宽度 是固定的,所以不使用length / bucketRange
      arr.forEach(item => {
        const index = Math.floor((item - min) / bucketRange)
        buckets[index].push(item)
      })
      let res = []
      buckets.forEach(item => {
        if(item.length >= 2) insertSort(item)
        res = res.concat(item)
      })
      return res
    }

基数排序

基数排序是在桶排序之上的一种排序方式,它将依照个位数大小开始排序并将排序完成之后的数组再按照十位数大小排序,然后是百位 / 千位...最后当需要排序的数组中的最大值小于 当前位数 的最小值时结束

代码实现

    // 基数排序
    function baseSort(arr) {
      const base = 10
      let divider = 1
      const max = Math.max(...arr)
      // 只要还有一个 大于等于 divider,就应该继续循环
      while(max >= divider) {
        const buckets = new Array(10).fill('').map(item => [])
        for(let i = 0; i < arr.length; i++) {
          const item = arr[i]
          const index = Math.floor(item / divider) % base
          console.log(buckets, index);
          buckets[index].push(item)
        }
        arr = [].concat(...buckets)
        divider *= 10
      }
      return arr
    }