三种简单的排序方法js实现

一、冒泡排序

冒泡排序规则

冒泡排序是最慢的排序算法之一,之所以叫冒泡排序是因为它会依次(假设这里是正序)遍历数据,并两两比较相邻数据,并按照升序(或降序)将较大(或小)的数据往右移动,这样最大(或最小)的数据就会像气泡一样慢慢浮动到顶端。假如这里有一组降序排序的数据 5,4,3,2,1,想要将它按升序排序,用冒泡排序的过程如下图:
三种简单的排序方法js实现_第1张图片

冒泡排序的代码实现:
function bubbleSort(arr) {
  var nums = arr.length;
  var temp = 0;
  for(var i = 0; i < nums - 1; i++) {
    for(var j = 0; j < nums - 1 - i; j++) { // 已经排好的数不需要比较,循环的次数越来越少
      if(arr[j] > arr[j + 1]) { // 两两比较,如果前面一个比后面一个大则交换位置
        temp = arr[j];
        arr[j] = arr[j+1];
        arr[j+1] = temp;
      }
    }
  }
  return arr;
}

二、选择排序

选择排序规则

选择排序按照升序(或降序)的方式从第一个数据开始(假设是正序遍历):
第一次循环:拿到第一个数据,将其与其后面的数据比较并选取较小(或较大)的数据。将选取的数据再与后面的数据比较…最后获得最小(或最大)数据与第一个数据互换位置。
第二次循环:获取第二个数据,将其与其后面的数据比较并选取较小(或较大)的数据…
最后获得最小(或最大)数据与第二个数据互换位置
以此类推

假设有一组数据 5,4,3,2,1,想要将它按升序排序,用选择排序的过程如下图:
三种简单的排序方法js实现_第2张图片

选择排序的代码实现:
function selectionSort(arr) {
  var nums = arr.length;
  var min = 0, temp = 0;
  for(var i = 0; i < nums - 1; i++) {
    min = i;
    for(var j = i + 1; j < nums; j++) {
      if(arr[j] < arr[min]) {
        min = j;
      }
    }
    if(min !== i) {
      temp = arr[min];
      arr[min] = arr[i];
      arr[i] = temp;
    }
  }
  return arr;
}

三、插入排序

插入排序规则

插入排序是在一个有序数列中,在正确的位置上插入一个数,使这个数列依旧有序。比如说分别写有1,3,5,2,4这些数字的卡片:
第一步:我们在桌子上先放个1,代表了原始的有序数列;
第二步:拿到了一个3,3比1大,放到1的右边({1, 3});
第三步:拿到了一个5,5比3大,放到3的右边({1, 3, 5});
第四步:拿到了一个2,2比3小比1大,将3以及后面的数字往右移,在3前面插入2({1, 2, 3, 5});
第五步:拿到了一个4,4比5小比3大,将5右移,在5前面插入4({1, 2, 3, 4, 5});

像上面的第四步,在已经排好的数据当中有1,3,5,我们一眼就能看出2介于1跟3之间。但我们在用代码去实现的时候,是不能马上就知道2到底要放在哪两个数之间的。因此我们需要将2去跟数组里面的j数(这里是从右往左)一个个去比对。

插入排序的代码实现:
// 从左往右排序
function insertSortFromLeft(arr) {
  var _length = arr.length, insertNum, temp;
  for(var i = 1; i  < _length; ++i) {
    insertNum= i; //将要插入的数据的起始位置,这里从数组的第二位开始,将数组的第一位认为原始的有序数据
    temp = arr[i];
    while(insertNum > 0 && temp < arr[insertNum - 1]) { // 将要插入的数据与它的前面一位(即为已排序号的数据)比较
      arr[insertNum] = arr[insertNum - 1]; // 如果将要插入的数据比已排序好数据的最右侧数据小,则将后者向右移动一位
      insertNum--;
    }
    arr[insertNum] = temp;
  }
}

从右往左排序
function insertSortFromRight(arr) {
  var _length = arr.length, insertNum, temp;
  for(var i = _length - 2; i > -1; --i) {
    insertNum = i; 
    temp = arr[i];
    while(insertNum < _length - 1 && temp > arr[insertNum + 1]) {
      arr[insertNum] = arr[insertNum + 1];
      insertNum++;
    }
    arr[insertNum] = temp;
  }
}

四、三种排序的时间比较

生成数组

function generateArr(len) {
  var arr = [];
  for(var i = 0; i < len; i++) {
    arr[i] = Math.floor(Math.random()*len + 1);
  }
  return arr;
}

const data100 = generateArr(100);
const data1000 = generateArr(1000);
const data10000 = generateArr(10000);

console.time('100个元素冒泡排序用时:');
bubbleSort(data100);
console.timeEnd('100个元素冒泡排序用时:');

console.time('100个元素选择排序用时:');
selectionSort(data100);
console.timeEnd('100个元素选择排序用时:');

console.time('100个元素插入排序用时:');
insertSort(data100);
console.timeEnd('100个元素插入排序用时:');

console.time('1000个元素冒泡排序用时:');
bubbleSort(data1000);
console.timeEnd('1000个元素冒泡排序用时:');

console.time('1000个元素选择排序用时:');
selectionSort(data1000);
console.timeEnd('1000个元素选择排序用时:');

console.time('1000个元素插入排序用时:');
insertSort(data1000);
console.timeEnd('1000个元素插入排序用时:');

console.time('10000个元素冒泡排序用时:');
bubbleSort(data10000);
console.timeEnd('10000个元素冒泡排序用时:');

console.time('10000个元素选择排序用时:');
selectionSort(data10000);
console.timeEnd('10000个元素选择排序用时:');

console.time('10000个元素插入排序用时:');
insertSort(data10000);
console.timeEnd('10000个元素插入排序用时:');

由打印结果可知,当元素个数越来越多时,冒泡排序最慢,插入排序最快;而如果元素个数在100以内,那么他们的时间是差不多的。

你可能感兴趣的:(Data,Structure,and,Algorithms)