一、冒泡排序

排序规则:比较相邻元素,符合比较条件,交换位置较大的往后排,反复比较交换,直到所有数据都符合排序条件,得出排序效果,结束排序。

稳定性:稳定

排序动态示意:

代码实现:

var arr = [3,4,1,2,21,5,15,6,63];

function BubbleSort(ary){

for(var i = 0; i < ary.length - 1; i++){

for(var j = i + 1; j < ary.length; j++){

var current = ary[i];

if(current > ary[j]){

var tmp = ary[j];

ary[j] = current;

ary[i] = tmp;

}

}

}

return ary;

}

BubbleSort(arr); // [1, 2, 3, 4, 5, 6, 15, 21, 63]

二、选择排序

排序规则:通过比较,选出最小的数放在第一位,然后在其余所有的数中选出最小的数排在第二位,以此类推,直到排序结束。

稳定性:不稳定

排序动态示意:

代码实现:

var arr = [3,4,1,2,21,5,15,6,63];

function SelectSort(ary){

for(var i = 0; i < ary.length - 1; i++){

for(var j = i + 1; j < ary.length; j++){

if(ary[i] > ary[j]){

var tmp = ary[i];

ary[i] = ary[j];

ary[j] = tmp;

}

}

}

return ary;

}

SelectSort(arr); // [1, 2, 3, 4, 5, 6, 15, 21, 63]

三、插入排序

排序规则:插入排序得比喻成斗地主,手里摸牌之后都是按照从小到大的顺序。每摸到一张牌就把他们插入到合适的位置,使得他们比后面小,比前面大或者相等。

稳定性:稳定

排序动态示意:

代码实现:

var arr = [3,4,1,2,21,5,15,6,63];

function InsertSort(ary){

var temp;

for (var i = 1; i < ary.length; i++) {

for (var j = i-1; j >=0; j--) {

if (ary[j+1] < ary[j]) {

temp = ary[j+1];

ary[j+1] = ary[j];

ary[j] = temp;

} else if (ary[j+1] >= ary[j]) {

break;

}

}

}

return ary;

}

InsertSort(arr); // [1, 2, 3, 4, 5, 6, 15, 21, 63]

四、快速排序

排序规则:从数组中找一个基准值,通过这个值挨个和数组中的值进行比较,大的放一边,小的放一边,然后进行合并后,在进行比较,反复直至结束。

稳定性:不稳定

排序动态示意:

代码实现:

var arr = [3,4,1,2,21,5,15,6,63];

var quickSort = function(ary) {

if (ary.length <= 1) {

return ary;

}

var pivotIndex = Math.floor(ary.length / 2);

var pivot = ary.splice(pivotIndex, 1)[0];

var left = [];

var right = [];

for (var i = 0; i < ary.length; i++) {

if (ary[i] < pivot) {

left.push(ary[i]);

} else {

right.push(ary[i]);

}

}

return quickSort(left).concat([pivot], quickSort(right));

};

quickSort(arr); // [1, 2, 3, 4, 5, 6, 15, 21, 63]

五、堆排序

排序规则:堆是一棵顺序存储的二叉树,堆分为最大堆和最小堆,最大堆父节点都大于子节点, 最小堆父节点都小于子节点,左子节点: 2*i +1 (i: 父节点index),右子节点: 2*i+2,从最后一个非叶子节点开始将堆进行小顶堆排序,每次拿出根节点,并和最后一个节点进行交换,重新进行堆的建立。

稳定性:不稳定

排序动态示意:

代码实现:

var arr = [3,4,1,2,21,5,15,6,63];

function HeapSort(ary) {

// 实现最大堆

// start: 父节点, end: 循环深度

function maxHeap(ary, start, end) {

let parent = start, // 父节点

son = parent*2 + 1, // 左子节点

temp = null;

// 规定循序最大深度

while(son<=end) {

// 如果存在右子节点, 并且判断右节点是否大于左节点

if(son+1<=end && ary[son] < ary[son+1]) son++;

if(ary[son] > ary[parent]) {

temp = ary[son];

ary[son] = ary[parent];

ary[parent] = temp;

parent = son;

son = parent*2 +1;

}else {

return;

}

}

}

// 构建最大堆 ary.length/2-1: 表示最后一个父节点

for(let i = ary.length/2-1; i>=0; i--) {

maxHeap(ary, i, ary.length-1);

}

// 排序

for(let i = ary.length-1; i>0; i--) {

let temp = ary[0];

ary[0] = ary[i];

ary[i]= temp;

// 剔除最后一个元素,并复原最大堆

maxHeap(ary, 0, i-1);

}

return ary;

}

HeapSort(arr); // [1, 2, 3, 4, 5, 6, 15, 21, 63]

六、递并排序

排序规则:将长的数组分解为短的数组,一直分到最后,单个单个数组比较,我们就认为,只有一个元素的数组是有序的。然后再逐个的合并。

稳定性:稳定

排序动态示意:

代码实现:

var arr = [3,4,1,2,21,5,15,6,63];

function MergeSort(ary) { //采用自上而下的递归方法

var len = ary.length;

if(len < 2) {

return ary;

}

var middle = Math.floor(len / 2),

left = ary.slice(0, middle),

right = ary.slice(middle);

return merge(mergeSort(left), mergeSort(right));

}

function merge(left, right)

{

var 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;

}

MergeSort(arr); // [1, 2, 3, 4, 5, 6, 15, 21, 63]

七、希尔排序

排序规则:希尔排序是插入排序的一种更高效率的实现。它与插入排序的不同之处在于,它会优先比较距离较远的元素。希尔排序的核心在于间隔序列的设定。既可以提前设定好间隔序列,也可以动态的定义间隔序列。

稳定性:不稳定

排序动态示意:

代码实现:

var arr = [3,4,1,2,21,5,15,6,63];

function ShellSort(ary) {

var len = ary.length,

temp,

gap = 1;

while(gap < len/3) { //动态定义间隔序列

gap =gap*3+1;

}

for (gap; gap > 0; gap = Math.floor(gap/3)) {

for (var i = gap; i < len; i++) {

temp = ary[i];

for (var j = i-gap; j >= 0 && ary[j] > temp; j-=gap) {

ary[j+gap] = ary[j];

}

ary[j+gap] = temp;

}

}

return ary;

}

ShellSort(arr); // [1, 2, 3, 4, 5, 6, 15, 21, 63]

八、计数排序

排序规则:

1、找出待排序的数组中最大和最小的元素,然后建立一个数组C用于统计待排数组中最小元素到最大元素区间中每个元素出现次数;

2、统计数组中每个值为i的元素出现的次数,存入数组C的第i项;

3、对所有的计数累加(从C中的第一个元素开始,每一项和前一项相加);

4、反向填充目标数组:将每个元素i放在新数组的第C(i)项,每放一个元素就将C(i)减去1。

稳定性:稳定

排序动态示意:

代码实现:

var arr = [3,4,1,2,21,5,15,6,63];

function CountSort(ary){

let obj={};

for(let i=0; i

if(!obj[ary[i]]){

obj[ary[i]]=1;

}else{

obj[ary[i]]++;

}

}

let index=0;

//遍历对象属性名,按顺序放回覆盖原数组

for(let key in obj){

while(obj[key]>0){

ary[index]=Number(key);

obj[key]--;

index++

}

}

return ary;

}

CountSort(arr); // [1, 2, 3, 4, 5, 6, 15, 21, 63]