
---恢复内容开始---
一,冒泡排序。
具体算法描述如下:
<1>.比较相邻的元素。如果第一个比第二个大,就交换它们两个;
<2>.对每一对相邻元素作同样的工作,从开始第一对到结尾的最后一对,这样在最后的元素应该会是最大的数;
<3>.针对所有的元素重复以上的步骤,除了最后一个;
<4>.重复步骤1~3,直到排序完成。
代码实现
let arr = [9, 10, 8, 7, 5, 4, 2, 1, 3, 6]; function sort(arr) {
var as = [].concat(arr), len = arr.length, count = 0;
for (let i = 0; i < len-1; i++) {
for (let j = 0; j < len-1-i; j++) {
if(as[j]>as[j+1]){
var item = as[j];
as[j] = as[j+1];
as[j+1] = item;
count++;
}
}
}
console.log(count)
return as
}
console.log(sort(arr))
结果:
count:37
arr:[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
二,选择排序。
描述:
在时间复杂度上表现最稳定的排序算法之一,因为无论什么数据进去都是O(n²)的时间复杂度。。。所以用到它的时候,数据规模越小越好。唯一的好处可能就是不占用额外的内存空间了吧。
实现:
let arr = [9, 10, 8, 7, 5, 4, 2, 1, 3, 6]; function sort(arr) {
var as = [].concat(arr), len = arr.length, count = 0, minNum, item;
for (let i = 0; i < len-1; i++) {
minNum = i;
for (let j = i+1; j < len; j++) {
if(as[minNum] > as[j]){
minNum = j;
count++
}
}
item = as[i];
as[i] = as[minNum];
as[minNum] = item;
}
console.log(count)
return as
}
console.log(sort(arr))
三,插入排序。
描述:插入排序(Insertion-Sort)的算法描述是一种简单直观的排序算法。它的工作原理是通过构建有序序列,对于未排序数据,在已排序序列中从后向前扫描,找到相应位置并插入。插入排序在实现上,通常采用in-place排序(即只需用到O(1)的额外空间的排序),因而在从后向前扫描过程中,需要反复把已排序元素逐步向后挪位,为最新元素提供插入空间。
实现:
let arr = [9, 10, 8, 7, 5, 4, 2, 1, 3, 6]; function sort(arr) {
var as = [].concat(arr), len = arr.length, count = 0, preIndex, item;
for (let i = 1; i < len; i++) {
preIndex = i-1;
item = as[i];
while(preIndex >= 0 && as[preIndex] > item){
as[preIndex+1] = as[preIndex]
preIndex-- ;
count++;
}
as[preIndex+1] = item
}
console.log(count)
return as
}
console.log(sort(arr))
四,希尔排序。
描述:希尔排序本质上是一种插入排序,但是对数列进行了等间隔分组处理,在每一组中做插入排序,这一优化使得原本 O(n^2) 的时间复杂度一下降为 O(nlogn)
实现:
let arr = [9, 10, 8, 7, 5, 4, 2, 1, 3, 6];
function shellsort(arr) {
for (let gap = Math.floor(arr.length/2); gap > 0; gap = Math.floor(gap/2)) {
for (let i = gap; i < arr.length; i++) {
let item = arr[i];
let j = i-1;
while (j>=0 && arr[j] > item) {
arr[j+1] = arr[j];
j--;
}
arr[j+1] = item; }
}
}
console.log(shellsort(arr));
五,归并排序。
let arr = [9, 10, 8, 7, 5, 4, 2, 1, 3, 6];
function mergeSort(arr) {
if (arr.length<2) {
return arr
}
let middle =parseInt(arr.length/2);
let left = arr.slice(0,middle);
let right = arr.slice(middle);
if(left.length =='undefined' && right.length == 'undefined'){
return false
}
return merge(mergeSort(left),mergeSort(right))
} function merge(left,right) {
let result= []; while (left.length && right.length) {
if(left[0]<= right[0]){
result.push(left.shift())
}else{
result.push(right.shift())
}
}
while (left.length) {
result.push(left.shift())
}
while (right.length) {
result.push(right.shift())
}
return result
}
console.log(mergeSort(arr));
六,快速排序。
let arr = [9, 10, 8, 7, 5, 4, 2, 1, 3, 6];
function quickSort(arr) {
if(arr.length<=1){
return arr
}
let middle = Math.floor(arr.length/2);
let povid = arr.splice(middle,1)[0];
let left = [];
let right = [];
for (let i = 0; i < arr.length; i++) {
if(arr[i] < povid){
left.push(arr[i])
}else {
right.push(arr[i])
}
}
return quickSort(left).concat([povid],quickSort(right))
}
console.log(quickSort(arr))
七,堆排序。
//调整函数
function headAdjust(elements, pos, len){
//将当前节点值进行保存
var swap = elements[pos]; //定位到当前节点的左边的子节点
var child = pos * 2 + 1; //递归,直至没有子节点为止
while(child < len){
//如果当前节点有右边的子节点,并且右子节点较大的场合,采用右子节点
//和当前节点进行比较
if(child + 1 < len && elements[child] < elements[child + 1]){
child += 1;
} //比较当前节点和最大的子节点,小于则进行值交换,交换后将当前节点定位
//于子节点上
if(elements[pos] < elements[child]){
elements[pos] = elements[child];
pos = child;
child = pos * 2 + 1;
}
else{
break;
} elements[pos] = swap;
}
} //构建堆
function buildHeap(elements){
//从最后一个拥有子节点的节点开始,将该节点连同其子节点进行比较,
//将最大的数交换与该节点,交换后,再依次向前节点进行相同交换处理,
//直至构建出大顶堆(升序为大顶,降序为小顶)
for(var i=elements.length/2; i>=0; i--){
headAdjust(elements, i, elements.length);
}
} function sort(elements){
//构建堆
buildHeap(elements); //从数列的尾部开始进行调整
for(var i=elements.length-1; i>0; i--){
//堆顶永远是最大元素,故,将堆顶和尾部元素交换,将
//最大元素保存于尾部,并且不参与后面的调整
var swap = elements[i];
elements[i] = elements[0];
elements[0] = swap; //进行调整,将最大)元素调整至堆顶
headAdjust(elements, 0, i);
}
} var elements = [3, 1, 5, 7, 2, 4, 9, 6, 10, 8]; sort(elements);
console.log(elements);
八,计数排序。
function countingSort(array) {
let len = array.length,B = [],C = [],min = array[0], max = array[0];
for (var i = 0; i < len; i++) {
min = min <= array[i] ? min : array[i];
max = max >= array[i] ? max : array[i];
C[array[i]] = C[array[i]] ? C[array[i]] + 1 : 1;
} // 计算排序后的元素下标
for (var j = min; j < max; j++) {
C[j + 1] = (C[j + 1] || 0) + (C[j] || 0);
}
for (var k = len - 1; k >= 0; k--) {
B[C[array[k]] - 1] = array[k];
C[array[k]]--;
}
return B;
}
var elements = [3, 1, 5, 7, 2, 4, 9, 6, 10, 8]; console.log(countingSort(elements));
九,桶排序。
// @param array 数组
// @param num 桶的数量
function bucketSort(array, num) {
if (array.length <= 1) {
return array;
}
var len = array.length, buckets = [], result = [], min =array[0], max =array[0] , space, n = 0; var index = Math.floor(len / num) ;
while(index<2){ num--;
index = Math.floor(len / num) ;
} for (var i = 1; i < len; i++) {
min = min <= array[i] ? min : array[i];
max = max >= array[i] ? max : array[i];
}
space = (max - min + 1) / num; //步长
for (var j = 0; j < len; j++) {
var index = Math.floor((array[j] - min) / space);
if (buckets[index]) { // 非空桶,插入排序
var k = buckets[index].length - 1;
while (k >= 0 && buckets[index][k] > array[j]) {
buckets[index][k + 1] = buckets[index][k];
k--;
}
buckets[index][k + 1] = array[j];
} else { //空桶,初始化
buckets[index] = [];
buckets[index].push(array[j]);
}
}
while (n < num) {
result = result.concat(buckets[n]);
n++;
}
return result;
}
var elements = [3, 1, 5, 7, 2, 4, 9, 6, 10, 8]; console.log(bucketSort(elements,4));
十,基数排序。
/**
* 基数排序适用于:
* (1)数据范围较小,建议在小于1000
* (2)每个数值都要大于等于0
* @author damonare
* @param arr 待排序数组
* @param maxDigit 最大位数
*/
//LSD Radix Sort function radixSort(arr, maxDigit) {
var mod = 10;
var dev = 1;
var counter = [];
console.time('基数排序耗时');
for (var i = 0; i < maxDigit; i++, dev *= 10, mod *= 10) {
for(var j = 0; j < arr.length; j++) {
var bucket = parseInt((arr[j] % mod) / dev);
if(counter[bucket]== null) {
counter[bucket] = [];
}
counter[bucket].push(arr[j]);
}
var pos = 0;
for(var j = 0; j < counter.length; j++) {
var value = null;
if(counter[j]!=null) {
while ((value = counter[j].shift()) != null) {
arr[pos++] = value;
}
}
}
}
console.timeEnd('基数排序耗时');
return arr;
}
var elements = [3, 1, 5, 7, 2, 4, 9, 6, 10, 8]; console.log(radixSort(elements,2));