JS实现的计数排序与基数排序算法示例

可能需要先说明一下,计数排序和基数排序都是针对整数排序的算法。

1. 计数排序

计数排序的基本思想是将每个元素出现的次数统计出来,并按顺序排列。计数排序不是基于元素比较的,而是建立在元素的值域范围较小的前提下的。因此,计数排序的时间复杂度是O(n+k),其中k是元素的值域大小。

算法步骤

  1. 统计每个数字出现的次数,得到一个长度为k的计数数组。
  2. 将计数数组进行变形,使得第i个元素是所有小于等于i的元素出现次数的总和(从1开始累积),这样计数数组中的值就是元素排名。
  3. 开一个长度为n的排序数组,遍历原数组,将每个元素插入到排序数组中对应的位置,再将计数数组中对应元素的值-1。

示例1

假设有一个需要排序的数组arr为[1, 3, 2, 3, 2, 4, 1, 5, 2],值域为[1, 5]。

  1. 初始化长度为5的计数数组count为[0, 0, 0, 0, 0]。
  2. 遍历arr数组,对于每遇到一个数,则在count数组相应位置上加1。
遍历到1时,count数组变为 [1, 0, 0, 0, 0]
遍历到3时,count数组变为 [1, 0, 0, 1, 0]
遍历到2时,count数组变为 [1, 0, 1, 1, 0]
遍历到3时,count数组变为 [1, 0, 1, 2, 0]
遍历到2时,count数组变为 [1, 0, 2, 2, 0]
遍历到4时,count数组变为 [1, 0, 2, 2, 1]
遍历到1时,count数组变为 [2, 0, 2, 2, 1]
遍历到5时,count数组变为 [2, 0, 2, 2, 2]
遍历到2时,count数组变为 [2, 0, 3, 2, 2]
  1. 对于计数数组count进行变形,累加每个位置前面的元素。在本例中,累加后的计数数组count变为[2, 2, 5, 7, 9]。
  2. 创建一个长度为9的新数组sorted,遍历原始数组arr,将数字按照排名依次放入新数组中。
第一次取数字1,由于该数的排名为2,所以将该数放到sorted数组的索引为1的位置。
第二次取数字3,由于该数的排名为5,所以将该数放到sorted数组的索引为5的位置。
第三次取数字2,由于该数的排名为3,所以将该数放到sorted数组的索引为3的位置。
第四次取数字3,由于该数的排名为5,所以将该数放到sorted数组的索引为6的位置。 
第五次取数字2,由于该数的排名为3,所以将该数放到sorted数组的索引为4的位置。
第六次取数字4,由于该数的排名为7,所以将该数放到sorted数组的索引为7的位置。
第七次取数字1,由于该数的排名为2,所以将该数放到sorted数组的索引为2的位置。
第八次取数字5,由于该数的排名为9,所以将该数放到sorted数组的索引为9的位置。
第九次取数字2,由于该数的排名为3,所以将该数放到sorted数组的索引为5的位置。

排序后的数组为[1, 1, 2, 2, 2, 3, 3, 4, 5]

示例2

function countingSort(arr) {
  let max = Math.max(...arr);
  let count = new Array(max + 1).fill(0);
  for (let num of arr) {
    count[num]++;
  }
  let sortedIndex = 0;
  for (let i = 0; i <= max; i++) {
    while (count[i] > 0) {
      arr[sortedIndex++] = i;
      count[i]--;
    }
  }
  return arr;
}

该示例代码演示了计数排序的基本实现,时间复杂度为O(n+k)。函数接收一个数组参数arr,返回排好序的数组。对于每个数字num,遍历数组并将计数数组对应位置+1。然后根据计数数组,将所有数字放入排序数组中。函数内使用了一个while循环来处理数字重复的情况。

2. 基数排序

基数排序的基本思想是将整数按位数切割成不同的数字,然后按每个位数分别进行比较排序,最终实现全局排序。基数排序属于非比较排序算法,时间复杂度为O(dn),其中d是数字位数。通常情况下,基数排序用于对整数进行排序。

算法步骤

  1. 取得操作数的最大位数,假设是k位。
  2. 对数组从最低位开始(第1位)进行排序。
  3. 从最低位排到最高位。
  4. 排序使用的方法:用10个桶依次分别对个位、十位、百位...进行排序。

示例1

假设有一个需要排序的数组arr为[3, 30, 34, 5, 9]。

  1. 取得数组arr的位数的最大值max,max为2位。
  2. 从低位到高位,分别按每一位进行排序。
  3. 对于本例,首先按照个位排序,将每个数字放入桶中,按照桶的顺序将数字取出,并按照个位排序。排序后的数组为[30, 5, 9, 3, 34]。
  4. 接下来按照十位排序,将每个数字放入桶中,按照桶的顺序取出数字,再按照个位排序。排序后的数组为[3, 30, 34, 5, 9]。
  5. 排序完成,最终数组为[3, 30, 34, 5, 9]。

示例2

function radixSort(arr) {
  const max = Math.max(...arr);
  const maxDigit = String(max).length;
  let mod = 10;
  let dev = 1;
  for (let i = 0; i < maxDigit; i++, dev *= 10, mod *= 10) {
    let bucketList = new Array(10).fill([]);
    for (let j = 0; j < arr.length; j++) {
      let num = parseInt(arr[j] % mod / dev);
      let bucket = bucketList[num];
      bucket.push(arr[j]);
      bucketList[num] = bucket;
    }
    let res = [];
    for (let j = 0; j < bucketList.length; j++) {
      res.push(...bucketList[j]);
    }
    arr = res;
  }
  return arr;
}

该示例代码演示了基数排序的基本实现,时间复杂度为O(dn)。函数接收一个数组参数arr,返回排好序的数组。函数内的dev和mod用来分别获取数字每一位数值,在每次排序的循环中创建一个长度为10的二维桶bucketList。对于每个数字num,首先计算其在当前位的值,然后将其放入对应的桶上。排序完成后,将bucketList中的数字依次放入一个新数组res中,返回res。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:JS实现的计数排序与基数排序算法示例 - Python技术站

(0)
上一篇 2023年5月19日
下一篇 2023年5月19日

相关文章

  • 又一个PHP实现的冒泡排序算法分享

    下面我将详细讲解一下“又一个PHP实现的冒泡排序算法分享”的完整攻略。 前言 冒泡排序是一种简单直观的排序方法,它重复地走访过要排序的数列,每次比较相邻的两个元素,如果它们的顺序错误就把它们交换过来。 原理 冒泡排序的原理主要包括以下两个步骤: 比较相邻的元素,如果第一个比第二个大,就交换它们两个; 对每一对相邻元素重复执行步骤 1,直到最后一对元素。这样做…

    算法与数据结构 2023年5月19日
    00
  • go实现冒泡排序算法

    下面是详细讲解Go语言实现冒泡排序算法的完整攻略: 1. 什么是冒泡排序? 冒泡排序是一种基于交换的排序算法,算法通过比较相邻的元素,将比较大的元素交换到后面,从而达到排序的目的。这个过程就像是水中不断上冒的气泡,因此称之为冒泡排序。 冒泡排序是经典的排序算法之一,它虽然时间复杂度高达 O(n^2),但其思想简单,易于理解和实现,并且在某些特殊的情况下,它的…

    算法与数据结构 2023年5月19日
    00
  • c++深入浅出讲解堆排序和堆

    C++深入浅出讲解堆排序和堆 堆的定义 堆是一种特殊的树形数据结构,它满足以下两个特性: 堆是一个完全二叉树(Complete Binary Tree); 堆中每个节点的值都大于等于(或小于等于)其左右子节点的值。 可以看出,堆一般分为两种类型:大根堆(Max Heap)和小根堆(Min Heap)。大根堆的每个节点的值都大于等于其左右子节点的值,小根堆则相…

    算法与数据结构 2023年5月19日
    00
  • java图搜索算法之图的对象化描述示例详解

    Java图搜索算法之图的对象化描述示例详解 什么是图? 图是一种非线性数据结构,由节点和边组成,节点表示图中对象,边表示节点间相互关系。图分为有向图和无向图,有向边和无向边。 图的对象化描述 Java中可以使用对象化的方式来描述一个图,主要有两个类: Vertex(节点类) 节点类表示图中的节点,主要有两个属性: label:节点标签,用于区分不同节点。 w…

    算法与数据结构 2023年5月19日
    00
  • python 如何在list中找Topk的数值和索引

    对于如何在Python的list中找Topk的数值和索引,可以采用以下方法: 方法一:使用sorted函数排序 可以使用Python内置的sorted函数对list进行排序,然后取前k个元素,同时得到它们的索引。具体代码如下: lst = [3, 1, 4, 1, 5, 9, 2, 6, 5, 3, 5] k = 3 # 记录每个元素的索引和值 lst_wi…

    算法与数据结构 2023年5月19日
    00
  • C语言简单实现快速排序

    C语言简单实现快速排序 什么是快速排序? 快速排序(Quicksort)是一种分治的排序算法,由Tony Hoare于1960年提出。快速排序使用两个指针i,j分别指向待排序数组的最左侧和最右侧,以一个值作为基准(pivot),一般为数组的中间值。快速排序的主要思路是将数组中小于基准值的数放到基准值左边,将大于基准值的数放到右边。然后通过递归的方式,对左右两…

    算法与数据结构 2023年5月19日
    00
  • c++入门必学库函数sort的基本用法

    一、sort函数的基本介绍 sort()函数是C++ STL标准库提供的一种排序函数,能够对数组或容器进行排序。可以用于排序基本数据类型、结构体、对象等各种数据类型。其中,数组的排序时简单易行的,容器的排序则更加强大方便。 sort()的函数原型如下: template<class RandomAccessIterator> void sort(…

    算法与数据结构 2023年5月19日
    00
  • TypeScript调整数组元素顺序算法

    下面是详细的攻略: TypeScript调整数组元素顺序算法 在 TypeScript 中实现调整数组元素顺序的算法需要使用到以下两种方法: 方法一:splice() array.splice(startIndex, toRemove, …itemsToAdd) splice() 方法可以实现对数组中指定起始索引 startIndex 开始的若干元素的删…

    算法与数据结构 2023年5月19日
    00
合作推广
合作推广
分享本页
返回顶部