深入探密Javascript数组方法


Posted in Javascript onJanuary 08, 2015

在JavaScript中,数组可以使用Array构造函数来创建,或使用[]快速创建,这也是首选的方法。数组是继承自Object的原型,并且他对typeof没有特殊的返回值,他只返回'object'。

1. Array.prototype.slice方法
数组的 slice 方法通常用来从一个数组中抽取片断。不过,它还有将“类数组”(比如arguments和​HTMLCollection​)转换为真正数组的本领。

 var nodesArr = Array.prototype.slice.call(document.forms);

 var argsArr = Array.prototype.slice.call(arguments);

我就好奇了为什么数组的slice方法有这样的本领,它在javascript引擎中是如何实现的?slice的兄弟方法有没有这样的本领?

带着好奇心,下载Google的V8 javascript引擎源码到本地,V8源码的下载地址:https://github.com/v8/v8。

在v8-master/src/array.js中查找“Array.prototype.slice”:

function ArraySlice(start, end) {

  CHECK_OBJECT_COERCIBLE(this, "Array.prototype.slice");

  ...

  var result = []; // 这句是关键

  if (end_i < start_i) return result;

  if (UseSparseVariant(array, len, IS_ARRAY(array), end_i - start_i)) {

     ...

    SparseSlice(array, start_i, end_i - start_i, len, result);

  } else {

    SimpleSlice(array, start_i, end_i - start_i, len, result);

  }

  ...

  return result;

接着猜想调用“类数组”走的应该是SimpleSlice方法,然后在源码查找“SimpleSlice“,发现Array.prototype.splice源码中也调用了SimpleSlice方法,且结果变量也初始化为空数组。不过,想用splice方法把“类数组”转化为真正数组,必须要传入起始位置参数为0,即:

 var nodesArr = Array.prototype.splice.call(document.forms, 0);

因为它的实现原理就是将被删除的数组项组成新数组。感兴趣的童鞋可以看下Array.prototype.splice的源码实现。
此外,slice还可以克隆一个数组:

 var arr = [1, 2, 3];

 var cloneArr = arr.slice(); // cloneArr:  [1, 2, 3]

2. Array.prototype.push 方法
使用 push方法可以合并数组:

 var arr1 = [1, 'str', {name: 'lang'}];

 var arr2 = [2, 'ing'];

 Array.prototype.push.apply(arr1, arr2);

 // 返回结果:[1, "str", {name: 'lang'}, 2, "ing"]

3. Array.prototype.sort 方法
先上代码:

var arr = ['1', '2', '10', '12'];

arr.sort();

// 返回结果:["1", "10", "12", "2"]

上面的结果通常不是我们想要的,那么如何按数值大小排序:

arr.sort(function(a, b) {

  return a - b;

})

// 返回结果:["1", "2", "10", "12"]

有了排序比较器函数之后,就可以自定义很多比较器,从而实现个性化的排序。

4. length 属性
数组的length属性,不是只读的,也就说还可写哦,比如使用length属性去截断数组:

 var arr = [1, 2, 3, 4];

 arr.length = 2;

 // arr: [1, 2]

 arr.length = 0;

 // arr: []

与此同时,如果把length属性变大,数组的长度值变会增加,且使用undefined来作为新的元素填充。

 var arr = [];

 arr.length = 3;

 // arr: [undefined, undefined, undefined]

好了,今天就总结到这里了,已经凌晨了,以后有什么新发现再append到这里。
之前,没有写博客的习惯,只习惯把平时的总结放到有道云笔记中,没想到把观点写出来着实要花点心思的,因为要考虑如何表达,才能让别人更好地理解。

有什么表达不对或理解错误的地方,还望大家帮忙指正出来。

另附上一些常用的javascript数组方法

concat()连接两个或更多的数组,并返回结果。
join()把数组的所有元素放入一个字符串。元素通过指定的分隔符进行分隔。
pop()删除并返回数组的最后一个元素
push()向数组的末尾添加一个或更多元素,并返回新的长度。
reverse()颠倒数组中元素的顺序。
shift()删除并返回数组的第一个元素
slice()从某个已有的数组返回选定的元素
sort()对数组的元素进行排序
splice()删除元素,并向数组添加新元素。
toSource()返回该对象的源代码
toString()把数组转换为字符串,并返回结果。
toLocaleString()把数组转换为本地数组,并返回结果。
unshift()向数组的开头添加一个或更多元素,并返回新的长度。
valueOf()返回数组对象的原始值

Javascript 相关文章推荐
JS小游戏之仙剑翻牌源码详解
Sep 25 Javascript
jQuery中live()方法用法实例
Jan 19 Javascript
JavaScript使ifram跨域相互访问及与PHP通信的实例
Mar 03 Javascript
js显示动态时间的方法详解
Aug 20 Javascript
thinkphp标签实现bootsrtap轮播carousel实例代码
Feb 19 Javascript
详解Node.js开发中的express-session
May 19 Javascript
Angular移动端页面input无法输入的解决方法
Nov 14 Javascript
jquery ajaxfileupload异步上传插件
Nov 21 jQuery
解决VUEX兼容IE上的报错问题
Mar 01 Javascript
JavaScript实现表单注册、表单验证、运算符功能
Oct 15 Javascript
微信小程序后端无法保持session的原因及解决办法问题
Mar 20 Javascript
微信小程序调用wx.getImageInfo遇到的坑解决
May 31 Javascript
用模版生成HTML的的框架jquery.tmpl使用详解
Jan 07 #Javascript
jQuery中parentsUntil()方法用法实例
Jan 07 #Javascript
jQuery中parents()方法用法实例
Jan 07 #Javascript
jQuery中parent()方法用法实例
Jan 07 #Javascript
jQuery中nextUntil()方法用法实例
Jan 07 #Javascript
jQuery中nextAll()方法用法实例
Jan 07 #Javascript
jQuery中next()方法用法实例
Jan 07 #Javascript
You might like
PHP面向对象程序设计方法实例详解
2016/12/24 PHP
TP5框架页面跳转样式操作示例
2020/04/05 PHP
Javascript+XMLHttpRequest+asp.net无刷新读取数据库数据
2009/08/09 Javascript
为jquery.ui.dialog 增加“在当前鼠标位置打开”的功能
2009/11/24 Javascript
实现图片预加载的三大方法及优缺点分析
2014/11/19 Javascript
浅谈js中的闭包
2015/03/16 Javascript
Jquery ajax加载等待执行结束再继续执行下面代码操作
2015/11/24 Javascript
js实现select下拉框菜单
2015/12/08 Javascript
JS实现的在线调色板实例(附demo源码下载)
2016/03/01 Javascript
javascript html5移动端轻松实现文件上传
2020/03/27 Javascript
JS字符串false转boolean的方法(推荐)
2017/03/08 Javascript
AngularJS实现根据不同条件显示不同控件
2017/04/20 Javascript
JS简单实现数组去重的方法分析
2017/10/14 Javascript
vue项目打包之后背景样式丢失的解决方案
2019/01/17 Javascript
[原创]微信小程序获取网络类型的方法示例
2019/03/01 Javascript
JavaScript字符串处理常见操作方法小结
2019/11/15 Javascript
vue 遮罩层阻止默认滚动事件操作
2020/07/28 Javascript
vue编写简单的购物车功能
2021/01/08 Vue.js
python实现简单socket通信的方法
2016/04/19 Python
python difflib模块示例讲解
2017/09/13 Python
TF-IDF与余弦相似性的应用(一) 自动提取关键词
2017/12/21 Python
Python之两种模式的生产者消费者模型详解
2018/10/26 Python
Python推导式简单示例【列表推导式、字典推导式与集合推导式】
2018/12/04 Python
对Django中static(静态)文件详解以及{% static %}标签的使用方法
2019/07/28 Python
关于PyTorch源码解读之torchvision.models
2019/08/17 Python
Python 图片处理库exifread详解
2021/02/25 Python
CSS3中的元素过渡属性transition示例详解
2016/11/30 HTML / CSS
教师实习自我鉴定
2013/12/13 职场文书
师范教师毕业鉴定
2014/01/13 职场文书
英语三分钟演讲稿
2014/08/19 职场文书
机关党员三严三实心得体会
2014/10/13 职场文书
2019开业庆典剪彩仪式主持词!
2019/07/22 职场文书
redis三种高可用方式部署的实现
2021/05/11 Redis
JavaScript 数组去重详解
2021/09/15 Javascript
灵能百分百第三季什么时候来?
2022/03/15 日漫
如何在Python中妥善使用进度条详解
2022/04/05 Python