使用不同的方法结合/合并两个JS数组


Posted in Javascript onSeptember 18, 2014

这是一篇简单的文章,关于JavaScript数组使用的一些技巧。我们将使用不同的方法结合/合并两个JS数组,以及讨论每个方法的优点/缺点。

让我们先考虑下面这情况:

var a = [ 1, 2, 3, 4, 5, 6, 7, 8, 9 ];

var b = [ "foo", "bar", "baz", "bam", "bun", "fun" ];

很显然最简单的结合结果应该是:
[

1, 2, 3, 4, 5, 6, 7, 8, 9,

"foo", "bar", "baz", "bam" "bun", "fun"

]
concat(..)
这是最常见的做法:
var c = a.concat( b );

a; // [1,2,3,4,5,6,7,8,9]

b; // ["foo","bar","baz","bam","bun","fun"]

c; // [1,2,3,4,5,6,7,8,9,"foo","bar","baz","bam","bun","fun"]
正如你所看到的,C是一个全新的数组,表示a和b两个数组的组合,并让A和B不变。简单吧?

但如果a有10,000个元素,而b也有一万个元素? C就会有2万个元素,所以a和b的内内存使用就会翻倍。

“没问题!”,你说。让它们被垃圾回收,把A和B设置为null,问题解决了!

a = b = null; // 'a'和'b'就被回收了

呵呵。对于只有几个元素的小数组,这没啥问题。但对于大数组,或者在内存有限的系统中需要经常重复这个过程,它其实还有很多改进的地方。
循环插入

好吧,让我们将一个数组的内容复制到另一个,使用: Array#push(..)

// `b` onto `a`

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

a.push( b[i] );

}

a; // [1,2,3,4,5,6,7,8,9,"foo","bar","baz","bam","bun","fun"]

b = null;
现在,数组a有了数组b的内容。

似乎有更好的内存占用。

但如果a数组比较小?出于内存和速度的原因,你可能要把更小的a放到b的前面,。没问题,只需将push(..)换成unshift(..)即可:

// `a` into `b`:

for (var i=a.length-1; i >= 0; i--) {

b.unshift( a[i] );

}

b; // [1,2,3,4,5,6,7,8,9,"foo","bar","baz","bam","bun","fun"]

功能技巧

不过for循环确实比较丑,而且不好维护。我们可以做的更好吗?

这是我们的第一次尝试,使用Array#reduce:

// `b` onto `a`:

a = b.reduce( function(coll,item){

coll.push( item );

return coll;

}, a );
a; // [1,2,3,4,5,6,7,8,9,"foo","bar","baz","bam","bun","fun"]

// or `a` into `b`:

b = a.reduceRight( function(coll,item){

coll.unshift( item );

return coll;

}, b );

b; // [1,2,3,4,5,6,7,8,9,"foo","bar","baz","bam","bun","fun"]

Array#reduce(..) 和 Array#reduceRight(..)是不错的,但他们是一点点笨拙。 ES6=>的箭头函数将减少一些代码量,但它仍然需要一个函数,每个元素都需要调用一次,不是很完美。

那这个怎么样:

// `b` onto `a`:
a.push.apply( a, b );

a; // [1,2,3,4,5,6,7,8,9,"foo","bar","baz","bam","bun","fun"]

// or `a` into `b`:

b.unshift.apply( b, a );

b; // [1,2,3,4,5,6,7,8,9,"foo","bar","baz","bam","bun","fun"]

这是一个要好很多吧?特别是因为 unshift(..)方法在这里并不需要担心前面的反向排序。 ES6的spead操作会更漂亮: a.push( ...b ) 或 b.unshift( ...a

数组最大长度限制

第一个主要的问题是,内存使用量增长了一倍(当然只是暂时的!)被追加内容基本上是通过函数调用将元素复制到堆栈中。此外,不同的JS引擎都有拷贝数据长度的限制。

所以,如果数组有一百万个元素,你肯定会超出了push(...)或unshift(...)允许调用堆栈的限制。唉,处理几千个元素它会做得很好,但你必须要小心,不能超过合理的长度限值。

注意: 你可以尝试一下splice(...),它跟push(...)和unshift(...)一样都有这种问题。

有一种方法可以避免这种最大长度限制。

function combineInto(a,b) {

var len = a.length;

for (var i=0; i < len; i=i+5000) {

b.unshift.apply( b, a.slice( i, i+5000 ) );

}

}
等一下,我们的可读性倒退了。 就这样吧,可能会越改越差,呵。
Javascript 相关文章推荐
JavaScript中为元素加上name属性的方法
May 09 Javascript
js捕获鼠标滚轮事件代码
Dec 16 Javascript
jQuery简单实现banner图片切换
Jan 02 Javascript
让你一句话理解闭包(简单易懂)
Jun 03 Javascript
AngularJS基础 ng-cloak 指令简单示例
Aug 01 Javascript
分享JS数组求和与求最大值的方法
Aug 11 Javascript
JavaScript将base64图片转换成formData并通过AJAX提交的实现方法
Oct 24 Javascript
详解获取jq ul第一个li定位的四种解决方案
Nov 23 Javascript
详解性能更优越的小程序图片懒加载方式
Jul 18 Javascript
elementUI select组件默认选中效果实现的方法
Mar 25 Javascript
原生js实现的移动端可拖动进度条插件功能详解
Aug 15 Javascript
jQuery实现轮播图效果demo
Jan 11 jQuery
js实现按Ctrl+Enter发送效果
Sep 18 #Javascript
javascript搜索框点击文字消失失焦时文本出现
Sep 18 #Javascript
输入框过滤非数字的js代码
Sep 18 #Javascript
小结Node.js中非阻塞IO和事件循环
Sep 18 #Javascript
JavaScript将取代AppleScript?
Sep 18 #Javascript
Javascript MVC框架Backbone.js详解
Sep 18 #Javascript
JS回调函数的应用简单实例
Sep 17 #Javascript
You might like
php将字符串转换成16进制的方法
2015/03/17 PHP
Yii扩展组件编写方法实例分析
2015/06/29 PHP
php调用自己java程序的方法详解
2016/05/13 PHP
php getcwd与dirname(__FILE__)区别详解
2016/09/24 PHP
利用php_imagick实现复古效果的方法
2016/10/18 PHP
详解PHP PDO简单教程
2019/05/28 PHP
jQuery中创建实例与原型继承揭秘
2011/12/21 Javascript
33个优秀的 jQuery 图片展示插件分享
2012/03/14 Javascript
javaScript复制功能调用实现方案
2012/12/13 Javascript
JS保留两位小数 四舍五入函数的小例子
2013/11/20 Javascript
多种方法实现load加载完成后把图片一次性显示出来
2014/02/19 Javascript
JQuery选择器绑定事件及修改内容的方法
2015/01/23 Javascript
jQuery给多个不同元素添加class样式的方法
2015/03/26 Javascript
大型JavaScript应用程序架构设计模式
2016/06/29 Javascript
原生JS实现网络彩票投注效果
2016/09/25 Javascript
Angular+Bootstrap+Spring Boot实现分页功能实例代码
2017/07/21 Javascript
JavaScript输入分钟、秒倒计时技巧总结(附代码)
2017/08/17 Javascript
JQuery元素快速查找与操作
2018/04/22 jQuery
Vue实现左右菜单联动实现代码
2018/08/12 Javascript
node后端服务保活的实现
2019/11/10 Javascript
vue路由权限校验功能的实现代码
2020/06/07 Javascript
python下如何让web元素的生成更简单的分析
2008/07/17 Python
17个Python小技巧分享
2015/01/23 Python
Python实现的飞速中文网小说下载脚本
2015/04/23 Python
PyCharm MySQL可视化Database配置过程图解
2020/06/09 Python
pycharm + django跨域无提示的解决方法
2020/12/06 Python
Python实现淘宝秒杀功能的示例代码
2021/01/19 Python
美体小铺波兰官方网站:The Body Shop波兰
2019/09/03 全球购物
Dr. Martens马汀博士法国官网:马丁靴鼻祖
2020/01/15 全球购物
Python中如何定义一个函数
2016/09/06 面试题
招商经理岗位职责
2013/11/16 职场文书
《赠汪伦》教学反思
2014/04/12 职场文书
2014年村计划生育工作总结
2014/11/14 职场文书
优秀乡村医生事迹材料(2016精选版)
2016/02/29 职场文书
导游词之淮安明祖陵
2019/11/25 职场文书
Java实现经典游戏泡泡堂的示例代码
2022/04/04 Java/Android