Javascript [].slice.call与Array.prototype.slice.call
我最近一直在想 我过去使用过Javascript [].slice.call与Array.prototype.slice.call,javascript,performance,Javascript,Performance,我最近一直在想 我过去使用过[].slice.call或[].forEach.call。。。。等 我认为这样做很好,因为这样可以很容易地将数组之类的东西转换为数组 然而,我开始思考,最好是这样做: Array.prototype.slice.call或Array.prototype.forEach.call 我是否正确地认为,由于以下原因,这具有更好的性能: [].slice.call将创建一个空白数组,然后访问数组原型,稍后需要进行垃圾收集 Array.prototype.slice.call
[].slice.call
或[].forEach.call
。。。。等
我认为这样做很好,因为这样可以很容易地将数组之类的东西转换为数组
然而,我开始思考,最好是这样做:
Array.prototype.slice.call
或Array.prototype.forEach.call
我是否正确地认为,由于以下原因,这具有更好的性能:
[].slice.call
将创建一个空白数组,然后访问数组原型,稍后需要进行垃圾收集Array.prototype.slice.call
将直接调用Array-prototype方法,并且不会首先创建空白数组,然后遍历prototype树[].slice.call
比Array.prototype.slice.call
短,因此前者非常常见
正如@t.niese在评论中指出的,[].slice.call
创建了一个从未使用过的对象,即使它很可能不会对性能产生明显的影响
我想,如果担心性能,我更喜欢在外部作用域上创建一个带有bind
的快捷方式,然后使用它,而不是在Array.prototype.slice.call中使用[].slice.call来设置Array.prototype.slice.call的快捷方式:
var slice=Function.prototype.call.bind(Array.prototype.slice);
//然后就
函数doSomething(){
切片(参数);
切片(参数,1,-1);
}
切片(随便);
切片(无论如何,0,3);
//等等
结论
当然,正如在基准测试中所看到的,性能是不一样的
当性能真正重要时,只需对代码进行基准测试,根据您的需求对其进行优化
当性能无关紧要时,不必担心像这样的小改进,这是一个与代码风格相关的决定,因此选择您的个人偏好或遵循您正在工作的项目的代码风格指南
旁注
@Barmar在评论中发布了一个链接,内容也非常有趣。两个标准回复。首先,这不是你的瓶颈。第二,时间;我不知道哪个更快。我怀疑有些人喜欢[]
的主要原因只是因为它更短。@Barmar这就是我喜欢它的原因:)我不会使用[].slice.call
,而是将数组.prototype.slice
存储在本地var
中。我之所以不使用[].slice.call
是因为它创建了一个从未使用过的对象,即使它很可能不会对性能产生明显的影响。@JulienFouilhéArray.prototype.slice.call(参数或其他任何参数)
是将类似数组的对象(作为函数上的参数)转换为“true”数组。这是一个奇怪的测试:\u slcall=[].slice.call
。这将导致一个未定义的调用,而不是一个函数错误;test
@t.niese是的,第15版有点疯狂。第1版正好满足OP的好奇心。@laconbass我知道数组。prototype
应该更快一些,而且以前也遇到过jsperf。我只是想知道是否有一些明显的东西我忽略了或不知道。我想成为一名javascript开发人员所以我想知道一切:)如果var slice=Array.prototype.slice;slice.call(items);
比您的bind
示例(看起来也不错)更快/更慢,主要取决于js引擎本身。但无论如何,如果使用其中一个引擎会导致瓶颈,那么程序/工作流本身很可能存在更大的问题(将数组转换为数组对象后,数据也用于某些用途,此步骤通常比转换步骤花费更多的时间)@laconbass谢谢你的回答:)它确实带来了一些很好的讨论,对于任何碰巧发现这个问题的人来说都是非常好的!