1、冒泡排序
原理:通过依次比较两个相邻的元素,看两个元素是否满足大小关系要求,如果不满足则交换两个元素。每一次冒泡会让至少一个元素移动到它应该在的位置上,这样n次冒泡就完成了n个数据的排序工作。这个算法的名字是因为越小的元素会经由交换慢慢 “浮” 到数列的顶端。
let arr = [45, 15, 5, 48, 65, 456, 64, 23131, 123, 121, 31231, 231, 31, 4546];
function bubbling(arr) {
for (let i = 0; i < arr.length - 1; i++) {
for (let j = 0; j < arr.length - i - 1; j++) {
if (arr[j] > arr[j + 1]) {
let temp = arr[j + 1]
arr[j + 1] = arr[j]
arr[j] = temp
}
}
}
return arr
}
bubbling(arr)
// arr [ 5, 15, 31, 45, 48, 64, 65, 121, 123, 231, 456, 4546, 23131, 31231 ]
arr.length - i =>每一轮进行两个相邻元素交换完毕 就会出现最大值,然后出现第二大值,所有比较次数应该减去比较的当前轮数。
2、插入排序
原理:将原数组切割为有序数组(开始只有一个)和无序数组,然后依次让无序数组的元素与有序数组比较并插入,最后得到有序数组
let arr = [45, 1, 2, 45, 654, 64, 155, 4, 887, 897, 9, 798, 7897, 879, 89, 789, 987, 45, 6456, 456, 45, 6456, 12, 312, 123, 135, 4]
/**
* 插入排序
*/
function insertion(arr) {
let pxarr = arr.splice(0, 1);
arr.forEach(item => {
for (let i = 0; i < pxarr.length; i++) {
if (item > pxarr[i]) {
pxarr.splice(i, 0, item)
break;
}
}
});
return pxarr.reverse()
}
console.log(insertion(arr))
//[ 45,64, 89,123,135,155,312,456,654,789,798,879,887,897,987,6456,6456,7897 ]
3、选择排序
原理:将数组分为有序数组和无序数组,有序数组内开始为空,循环取无序数组中最小值,加入有序数组内,最后当无序数组内元素没有时,排序完成
// 选择排序
let arr = [45, 1, 2, 45, 654, 64, 155, 4, 887, 897, 9, 798, 7897, 879, 89, 789, 987, 45, 6456, 456, 45, 6456, 12, 312, 123, 135, 4]
function choose(arr) {
let sortArr = [];
while (arr.length) {
let min = Math.min(...arr)
sortArr.push(...arr.splice(arr.findIndex(item => item == min), 1))
}
return sortArr
}
console.log(choose(arr))
// Math.min(n1, n2, n3, ..., nX)
4、归并排序
5、快速排序
原理:快速排序的 原理是 在数组内找一个元素,作为基点,大于基点的数,右边数组放,小于基点的数,左边数组放,形成左边数组 基点 右边数组,再使用递归思想,左右两边再次使用快速排序
let arr = [45, 1, 2, 45, 654, 64, 155, 4, 887, 897, 9, 798, 7897, 879, 89, 789, 987, 45, 6456, 456, 45, 6456, 12, 312, 123, 135, 4]
// 快速排序
function querySort(arr) {
if (arr.length <= 1) {
return arr
}
const basePortIndex = Math.floor(arr.length / 2);
const basePort = arr.splice(basePortIndex, 1)[0]; // 删除数组中的基点
let left = [], right = [];
arr.forEach(item => {
if (item > basePort) {
right.push(item)
} else {
left.push(item)
}
})
return querySort(left).concat([basePort], querySort(right))
}
console.log(querySort(arr))
6、计数排序
原理:用排序数组内的值 当作计数数组的索引值,进行计数,重复出现+1
let arr = [45, 1, 2, 45, 654, 64, 155, 4, 887, 897, 9, 798, 7897, 879, 89, 789, 987, 45, 6456, 456, 45, 6456, 12, 312, 123, 135, 4]
// 计算排序
function countSort(arr) {
const countArr = [] // 创建一个计数的数组
arr.forEach(item => {
if (!countArr[item]) { //初始没有时 进行赋值为0
countArr[item] = 0
}
countArr[item]++ // 有即计数
})
const returnArr = []
countArr.forEach((item, index) => {
if (item) { // 只有大于1 即表示 有值的计数
while (item) {
returnArr.push(index)
item--;
}
}
})
return returnArr
}
console.log(countSort(arr))
6、桶排序
7、希尔排序