排序
冒泡排序
比较相邻的两个元素,如果前一个比后一个大,则交换位置。
第一轮把最大的元素放到了最后面。
由于每次排序最后一个都是最大的,所以之后按照步骤1排序最后一个元素不用比
1 2 3 4 5 6 7 8 9 10 11 | function bubble_sort(arr) { for ( let i = 0; i < arr.length; i++) { for ( let j = 0, temp; j < arr.length - i - 1; j++) { if (arr[j + 1] < arr[j]) { temp = arr[j]; arr[j] = arr[j + 1]; arr[j + 1] = temp; } } } console.log(arr); } bubble_sort([3, 8, 8, 4, 5, 2, 1, 1]); |
插入排序
过程类似于将牌桌上的牌拿到手中的过程(手中的牌始终保持升序)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | function insert_sort(arr) { // [0, i-1] 是手中的牌,[i, arr.length-1]是牌桌上的牌 // 一开始手中有一张牌 arr[0] for ( let i = 1; i < arr.length; i++) { // 始终保证 [0, i-1]的元素是升序 let val = arr[i]; // 从牌桌上拿一张牌 let right = i - 1; // 将其插入到手中牌的适当位置(手中较大的牌整体右移一位,如果手中牌均小,则不移动) while (right >= 0 && arr[right] > val) { arr[right + 1] = arr[right]; right--; } arr[right + 1] = val; } console.log(arr); } insert_sort([3, 8, 8, 4, 5, 2, 1, 1]); |
快速排序
核心就在递归
1. 划分: arr[i...j](包括arr[i] 和 arr[j])排序,随意取[i,j]中的一点p(如 p = (i + j) /2)则 将其划分为三段:arr[i...p-1] arr[p] arr[p+1...j]
2. 递归排序:将arr[i...p-1]中所有大于arr[p]的元素变换到 arr[p+1...j] 中,将 arr[p+1...j]中所有小于 arr[p]的元素变换到 arr[i...p-1]
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | function quick(arr, i, j) { // 范围 [i, j] if (i < j) { let q = split(arr, i, j); // 确保 范围 [i, q) 的值小于等于arr[q] 范围 [q+1, j]的值大于arr[q] quick(arr, i, q - 1); quick(arr, q + 1, j); } } function split(arr, i, j) { // 范围 [i, j] let val = arr[j], temp; let minAreaRight = i - 1; // 区域[i, minAreaRight]的值均小于等于val for ( let k = i; k < j; k++) { // 遍历完成后区域 [minAreaRight+1, k] 的值均大于val if (arr[k] <= val) { minAreaRight++; temp = arr[k]; arr[k] = arr[minAreaRight]; arr[minAreaRight] = temp; } } minAreaRight++; temp = arr[j]; arr[j] = arr[minAreaRight]; arr[minAreaRight] = temp; return minAreaRight; } quick([3, 8, 8, 4, 5, 2, 1, 1], 0, arr.length - 1); |
归并排序
1. 划分:将数组从中间划分为两部分,分别调用自身进行排序
2. 合并:将两段排好序的数组合并为一个排好序的数组
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | function merge_sort(arr, i, j) { // [i, j] if (i < j) { const mid = Math.floor(i + (j - i) / 2); merge_sort(arr, i, mid); merge_sort(arr, mid + 1, j); merge(arr, i, mid, j); } } function merge(arr, i, mid, j) { // [i, mid] 和 [mid+1, j] 分别已是升序 const leftArr = arr.slice(i, mid + 1), leftIndex = 0; const rightArr = arr.slice(mid + 1, j + 1), rightIndex = 0; leftArr.push(Number.MAX_SAFE_INTEGER); rightArr.push(Number.MAX_SAFE_INTEGER); for ( let k = i; k <= j; k++) { if (leftArr[leftIndex] <= rightArr[rightIndex]){ arr[k] = leftArr[leftIndex]; leftIndex++; } else { arr[k] = rightArr[rightIndex]; rightIndex++; } } } let arr = [3, 8, 8, 4, 5, 2, 1, 1]; merge_sort(arr, 0, arr.length - 1); console.log(arr); |
aa
aa
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· 三行代码完成国际化适配,妙~啊~
· .NET Core 中如何实现缓存的预热?