作为一个有追求的前端,忙里偷闲(闲得发慌)地复习了一下基础的排序算法,以此文留念.

本篇主要记录O(n²)复杂度的基础算法O(nlogn)的算法将在下次有空(闲得发慌)时更新

在记录时发现Es6语法中的解构赋值与传统的中间变量交换相比效率低下,经过几次测试发现其耗时大约为交换中间变量的两倍

1.冒泡排序

众所周知排序最基础的算法,也就是大名鼎鼎的冒泡了,为了方便日后回顾还是简单提一下冒泡的原理:

其核心思想在于不停地比较相邻元素的大小关系,如果前面的比后面的大则两个元素互换位置(此处以顺序为例);每当一次大的循环后总能将当前剩余数中最大的数交换到数组的末尾,类似于一个泡泡从底部浮出水面,故得名冒泡算法.下方代码为未使用任何优化的原始冒泡算法.

其时间复杂度为O(n²) 不需要额外空间;

 //冒泡排序
function BubbleSort(arr) {//arr即需要排序的数组;本文后续中的arr均为此意
console.time('timer');//用于统计代码执行时间
for (let i = 0; i < arr.length; i++) {
for (let j = 0; j < arr.length; j++) {
if (arr[j] > arr[j + 1])
[arr[j], arr[j + 1]] = [arr[j + 1], arr[j]];//交换元素(解构赋值ES6)
}
}
console.timeEnd('timer');
}

以一万个数构成的倒序(从大到小)数组变为顺序的时间如下图(与个人电脑及其它因素有关请勿较真)用解构赋值交换:

后续算法的时间均以同一数组测试

2.鸡尾酒排序

这种排序算法乃是对冒泡算法的一种小优化,其与冒泡的区别在于,在一趟排序中可以将一个最大的移到后端,同时将一个最小的移到前端,从而对冒泡算法进行优化

核心代码如下:

//鸡尾酒排序
function CocktailSort(arr) {
console.time('timer');
let [start, end] = [0, arr.length];
while (start < end) {
        //此循环与正常冒泡一致
for (let i = start; i < end; i++) {
if (arr[i] > arr[i + 1])
[arr[i], arr[i + 1]] = [arr[i + 1], arr[i]];
}
end--;//由于数组最后一位已经是最大的所以没有必要再让其参与后续的排序
for (let i = end - 1; i >= start; i--) {
if (arr[i] < arr[i - 1])
[arr[i], arr[i - 1]] = [arr[i - 1], arr[i]];
}
start++;
}
console.timeEnd('timer');
}

耗费时间如下

由于其本质与冒泡算法类似,虽然好上些许,但其本质仍为O(n²)的时间复杂度故时间并未得到太大的缩减(由于解构赋值的原因优化后的算法还不如不优化,是真的骚)

3.选择排序

选择排序也是大家所熟知的一种基础算法,其核心在于每一次选出最小(或最大)的一个数放到已经有序的数列后,经过如此重复操作后获得有序的数列

代码如下:

//选择排序
function SelecttionSort(arr) {
console.time('timer');
for (let i = 0; i < arr.length; i++) {
let min = i;//min表示当前最小值的下标
for (let j = i + 1; j < arr.length; j++) {
min = arr[j] < arr[min] ? j : min; //如果当前下标的值比arr[min]的值要小则以当前值替换
}
[arr[i], arr[min]] = [arr[min], arr[i]];
}
console.timeEnd('timer');
}

花费时间如下:

按理说同为n平方的复杂度时间耗费应该相差不大才对,结果由于交换次数的减少导致耗时大幅下降,感觉Js在这方面效率有点低

4.插入排序

插入排序的原理为将当前下标的数插入之前已经有序的数列中,从后往前遍历找到合适的位置后将值插入,并将该位置之后的元素依次后移从而进行排序

代码如下:

function InsertionSort(arr) {
console.time('timer');
for (let i = 1; i < arr.length; i++) {
for (let j = i; j > 0 && arr[j] < arr[j - 1]; j--) {
[arr[j], arr[j - 1]] = [arr[j - 1], arr[j]];
}
}
console.timeEnd('timer');
}

同数组耗时如下:

总结:在Js的情况下交换数据应尽量少的使用解构赋值,虽然其便利性很强,但是当网页对性能要求较高时应减少解构赋值的使用,如果非用不可,在同等级时间复杂度算法的情况下应使用数字交换次数少的算法以提升页面性能

JavaScript 基础排序的实现(一)的更多相关文章

  1. JavaScript 基础排序的实现(二)

    继上一篇O(n^2)的排序算法后,这一篇主要记录O(n*logn)的排序算法 1.快排(快速排序) 这一算法的核心思想为,先随机选一个数作为标兵或者说是标记(这个数一般来说选择该无序数组的中间那个元素 ...

  2. JavaScript基础

    JavaScript基础 JavaScript是一门编程语言,浏览器内置了JavaScript语言的解释器,所以在浏览器上按照JavaScript语言的规则编写相应代码之,浏览器可以解释并做出相应的处 ...

  3. 前端之JavaScript基础

    前端之JavaScript基础 本节内容 JS概述 JS基础语法 JS循环控制 ECMA对象 BOM对象 DOM对象 1. JS概述 1.1. javascript历史 1992年Nombas开发出C ...

  4. 一步步学习javascript基础篇(3):Object、Function等引用类型

    我们在<一步步学习javascript基础篇(1):基本概念>中简单的介绍了五种基本数据类型Undefined.Null.Boolean.Number和String.今天我们主要介绍下复杂 ...

  5. javascript基础部分

    javascript基础部分 1  数据类型: 基础数据类型(通过typeof来检测):Number,string,undefined,null,boolean,function typeof只能检测 ...

  6. 《JavaScript基础教程(第8版)》PDF

    简介:JavaScript基础教程(第8版)循序渐进地讲述了JavaScript及相关的CSS.DOM.Ajax.jQuery等技术.书中从JavaScript语言基础开始,分别讨论了图像.框架.浏览 ...

  7. JavaScript基础笔记二

    一.函数返回值1.什么是函数返回值    函数的执行结果2. 可以没有return // 没有return或者return后面为空则会返回undefined3.一个函数应该只返回一种类型的值 二.可变 ...

  8. 第三篇:web之前端之JavaScript基础

    前端之JavaScript基础   前端之JavaScript基础 本节内容 JS概述 JS基础语法 JS循环控制 ECMA对象 BOM对象 DOM对象 1. JS概述 1.1. javascript ...

  9. javascript基础、语法

    JavaScript基础(简介.语法) 一.JavaScript简介 1.JavaScript是个什么东西? 它是个脚本语言,需要有宿主文件,它的宿主文件是HTML文件. 2.它与Java什么关系? ...

随机推荐

  1. HNの野望

    1.标题 2.工作 3.学习 4.英语 5.健康 6.心理 7.绘画 8.看书

  2. ERRORS !MySQL 和 Javaweb 的报错合集

    ERROR:1175. You are using safe update mode and you tried to update a table without a WHERE that uses ...

  3. 7I - 数塔

    在讲述DP算法的时候,一个经典的例子就是数塔问题,它是这样描述的: 有如下所示的数塔,要求从顶层走到底层,若每一步只能走到相邻的结点,则经过的结点的数字之和最大是多少? 已经告诉你了,这是个DP的题目 ...

  4. 使用JS在页面进行数据处理时显示等待画面

    使用js在页面进行数据处理期间显示等待画面: 在页面选择执行函数进行数据处理期间,显示等待画面. <script> function fun(the,row_id) { //测试函数 // ...

  5. (摘录)Java 详解 JVM 工作原理和流程

    作为一名Java使用者,掌握JVM的体系结构也是必须的. 说起Java,人们首先想到的是Java编程语言,然而事实上,Java是一种技术,它由四方面组成:Java编程语言.Java类文件格式.Java ...

  6. MUI中超链接失效解决办法

    重新绑定a标签点击事件,用 plus.runtime.openURL(this.href) 打开新页面

  7. Hibernate中的实体规则、对象状态和进阶-一级缓存

    一.hibernate中的实体规则 1.实体类创建的注意事项 2.主键类型 3.主键生成策略 (1)代理主键 (2)自然主键 二.hibernate中的对象状态 1.对象分为三种状态 2.三种状态的转 ...

  8. 函数append()和html()的区别

    它们的功能缺失有点相似,但是实际上本质上是有区别: append()函数是为指定元素尾部附加内容,而html()函数是重置元素内部的html内容.·

  9. (PMP)第1章-----引论

    1.指南概述和目的: 2.基本要素: 项目:创造独特的产品,服务或成果而进行的临时性工作.特点:1.临时性   临时性并不一定意味着项目时间短.2.独特性   3.渐进明细性 项目管理:就是将知识,技 ...

  10. linux 环境统配

    #java JAVA_HOME=/opt/jdk CLASSPATH=$JAVA_HOME/lib/ PATH=$PATH:$JAVA_HOME/bin export PATH JAVA_HOME C ...