[] .slice或Array.prototype.slice

时间:2012-01-25 16:49:14

标签: javascript arrays object syntax prototype

我遇到了将Array原型应用于本机对象的两种方法:

arr = Array.prototype.slice.call(obj);
arr = [].slice.call(obj);

以类似的方式,获取类似于本机数组的对象的真实类型:

type = Object.prototype.toString.call(obj);
type = {}.toString.call(obj);

一个简单的测试:

function fn() {
    console.log(
        Array.prototype.slice.call(arguments),
        [].slice.call(arguments),
        Object.prototype.toString.call(arguments), 
        {}.toString.call(arguments)
    );
}

fn(0,1);

小提琴:http://jsfiddle.net/PhdmN/

他们看起来和我一模一样;第一种语法使用得更频繁,但第二种语法肯定更短。使用较短的语法时是否有任何缺点?

2 个答案:

答案 0 :(得分:26)

它们在功能上是相同的。

但是,Array对象可能会被覆盖,导致第一种方法失败。

//Example:
Array = {};
console.log(typeof Array.prototype.slice); // "undefined"
console.log(typeof [].slice);    // "function"

文字方法创建Array的新实例(与Array.prototype.方法相对)。两种方法的基准:http://jsperf.com/bbarr-new-array-vs-literal/3

当您打算多次使用该方法时,最佳做法是缓存方法:

  • var slice = Array.prototype.slice; //Commonly used
  • var slice = [].slice; - 如果您担心Array的存在,或者您只是喜欢较短的语法。

答案 1 :(得分:1)

这是一个有趣的问题!让我们分别介绍每种方法的优点(✔️)和缺点(❌):

  1. [].slice
    • ✔️:输入速度更快
      两次击键,没有 shift -修饰符或其他任何内容,
      您的短毛知道[.slice是错字。
    • ✔️:阅读速度更快
      您可以更快地确定相关部分(slice)。
    • ✔️:更受欢迎
      56M+ snippets on GitHub(截至2018年末)。
    • ✔️:不能被覆盖
      Rob's answer的第一部分对此进行了完美的演示。
    • ✔️:运行速度更快。
      等一下好吧,这实际上就是答案的重点。

与您所想并在各处阅读的内容完全相反, [].slice.call(...)不会实例化一个新的空Array只是为了访问其{{1 }}属性!

现在(已经超过5年了 –截至2018年底), JIT编译(1)包含在所有运行JavaScript的地方(除非您仍然使用IE8或更低版本浏览网页。

此机制允许JS引擎执行以下操作:(2)

  

...直接slice和{strong>静态解析为一次[].slice的直接引用,并且只有一个可配置的属性访问:Array.prototype

  1. forEach

    • ❌:输入速度较慢
      拼写错误(例如:Array.prototype.slice)在您尝试运行代码之前看起来还不错。
    • ❌:不太受欢迎
      8M+ snippets on GitHub(截至2018年末)。
    • ❌:运行速度较慢
      Array.prorotype.slice是:(2)

        

      ...查找整个范围,以获取Array.prototype.slice参考,直到遍历所有范围为止(直到全局一个...),因为您可以您随时可以命名变量Array

           

      达到全局范围并找到本机后,引擎将访问其proottype,然后访问其方法
        ...
        O(N)范围分辨率+ 2个属性访问权限(Array.prototype)。

    • ✔️:允许您无缝地适应将严格阻止您以.forEach([开头的行的任何编码约定
      绝对是一件好事。

    • ✔️:您不必解释为什么`几乎在所有方面都更好。
      尽管现在,它只是归结为
    • 下的clicking the share link

免责声明:请注意,实际上,任何一个都没有比另一个更有效地运行更快。这不是您应用程序的瓶颈。


  1. 您可能想阅读A crash course in just-in-time (JIT) compilers
  2. 引自 Andrea Giammarchi (Twitter上的@WebReflection