From 495acd3709a07bef8de74f96d22dfa42c34ffbfa Mon Sep 17 00:00:00 2001 From: yigencong Date: Wed, 28 Feb 2024 13:03:35 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=B7=BB=E5=8A=A0=E8=AE=A1=E6=95=B0?= =?UTF-8?q?=E6=8E=92=E5=BA=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- sort/count-sort.mjs | 60 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 60 insertions(+) create mode 100644 sort/count-sort.mjs diff --git a/sort/count-sort.mjs b/sort/count-sort.mjs new file mode 100644 index 0000000..ae2dd68 --- /dev/null +++ b/sort/count-sort.mjs @@ -0,0 +1,60 @@ +/** + * @description 计数排序, 只能对大于零的整数排序 + * @param {number[]} arr - 需要排序的数组 + */ +export function countSort(arr) { + const len = arr.length; + const counts = []; // 用于计数的数组 + // 遍历整个数组 + for (let i = 0; i < len; i++) { + const el = arr[i]; + counts[el] = counts[el] ? counts[el] + 1 : 1; + } + let index = 0; + for (let i = 0; i < counts.length; i++) { + let time = counts[i]; + while (time) { + // 当桶子不为空时,遍历time次 + arr[index++] = i; + time--; + } + } + return arr; // 返回与不反都可以,本身就是对原数组的操作 +} + +/** + * @description 修改后的计数排序,支持负数 + * @param {number[]} arr - 要排序的整数数组 + */ +export function countSort2(arr) { + // 先找出最大值和for + const n = arr.length; + let min = arr[0]; + let max = arr[0]; + for (let i = 0; i < n; i++) { + if (arr[i] > max) { + max = arr[i]; + } + if (arr[i] < min) { + min = arr[i]; + } + } + // 计算计数数组的大小 + const size = max - min + 1; + const counts = new Array(size).fill(0); + // 遍历原数组把"值-min"作为计数数组的下标, 值-min能保证下标永 远不会小于零 + for (let i = 0; i < n; i++) { + counts[arr[i] - min]++; + } + // 遍历counts数组, 累计前面的下下标值 + for (let i = 1; i < size; i++) { + counts[i] += counts[i - 1]; + } + const ret = [];// 排序后的新数组 + // 现在数组的下表就是值,值就是下标 + for (let i = n - 1; i >= 0; i--) { + counts[arr[i] - min]--; // 假设我们有三个数放入counts中,counts[0]=1,counts[1]=2,counts[2]=3,所以要先减1再做下标使用 + ret[counts[arr[i] - min]] = arr[i]; + } + return ret; +}