【问题标题】:javascript var statement and performancejavascript var 语句和性能
【发布时间】:2012-03-29 04:20:46
【问题描述】:

选项1:多个无赋值的变量

function MyFunction() {

  var a = null;
  var b = null;
  ....
  var z = null;

  a = SomeValue;
  b = SomeValue2;
  ....
}

选项 2:一个 var 语句,无赋值

function MyFunction() {

  var a, b ..., z;

  a = SomeValue;
  b = SomeValue2;
  ....
}

选项 3:带赋值的多个 var 语句

function MyFunction() {

  var a = SomeValue;
  var b = SomeValue2;
  ....
  var z = SomeValue26;
}

使用特定选项是否有任何性能优势?对于两个原始类型赋值 AND 对象引用赋值都是真的吗?

感谢您的意见。

【问题讨论】:

  • 我不知道性能差异,但在风格上我会选择选项 3。
  • 有很多事情可以进一步影响你的表现,你不应该为此烦恼......只要做你觉得更容易阅读的事情,因为这不会影响性能。另外,它可能会因您使用的 JS 引擎而异。
  • 请注意,选项 1 并不是您真正所说的。实际上有两个赋值:一次是当你声明变量并给它赋值null,然后是当你赋值SomeValue时。
  • 在声明时赋值要快得多(请参阅this jsPerf)。但是是否使用多个 var 语句并不重要。

标签: javascript performance variable-declaration


【解决方案1】:

"过早的优化是 万恶之源”

我认为任何这些选项都不会有任何显着的性能变化。
(IMO)第三个选项是最易读的选项,最接近动态内存分配,如C# 等。但这是我的拙见,选择你最喜欢的。

如果它真的困扰您并且没有答案就无法入睡,请使用jsPerf 进行测试。


@Chad 发了一个jsPerf,这样你今晚就可以睡个好觉了……

【讨论】:

  • 在声明时赋值比先声明然后赋值快近 60% (jsPerf)
  • @乍得。添加了您的jsPerf。请注意,在chrome 所有中,结果完全相同相同!
  • @Chad 一年后我在 Chrome 29、FF 23 和 IE 10.0 中运行了该测试,还发现所有结果都在误差范围内(即完全相同)。
  • 是的,在 v20 之前的 FF 中存在细微差别。之后,所有浏览器的速度都是一样的。没有区别!
  • 源代码应该是可读的,让您选择的压缩器/编译器工具来完成这项肮脏的工作。
【解决方案2】:

要了解性能,您首先应该了解hoisting。让我们看下面的代码:

var x = 1;

function bar(val) {
    var returnVal = val * 2;

    return returnVal;
}

function foo(val) {
    var returnVal = 10;

    returnVal *= bar(val);

    return returnVal;
}

var y = foo(x);

console.log(y); // 20

提升基本上意味着 JavaScript 解释器会将变量声明“提升”到其范围的顶部。让这个例子看起来更像这样:

var x, y;

x = 1;

function bar(val) {
    var returnVal;

    returnVal = val * 2;

    return returnVal;
}

function foo(val) {
    var returnVal;

    returnVal = 10;
    returnVal *= bar(val);

    return returnVal;
}

y = foo(x);

console.log(y); // 20

因此,在您给出的示例中,选项 2 和 3 基本上会做同样的事情。因为解释器会将这些声明移到顶部。在这一点上,这是一个偏好的决定。很多人避免做类似var x, y, z; 的事情,说这很危险。我个人是这样做的。在我所处的任何范围内,我都会在顶部声明所有变量,然后在下面使用它们。但无论哪种方式都有效。

现在,您的第一个示例效率最低。吊装后是这样的:

function MyFunction() {
    var a, b, ... z;

    a = null;
    b = null;
    ...
    z = null;

    a = someValue;
    b = someValue2;
    ...
    z = someValueN;
}

这基本上会导致两次设置变量。

【讨论】:

    【解决方案3】:

    在 Chrome 中,execution times are identical

    这里唯一真正需要考虑的是优化网络传输

    考虑 var a=1;var b=2;...;var z=9;var a=1,b=2,...,z=9;

    如果您在每个标识符前面加上 ;var ,则为 5 个字节(假设为单字节字符编码),而 , 为 1 个字节。因此,声明 26 个变量,您可以通过编写一次 var  并用逗号列出标识符来节省 100 个字节。

    当然,这并不是一个巨大的节省,但是当涉及到通过网络推送比特时,每个字节都有帮助。这没什么好担心的,但是如果您发现自己在同一区域中声明了多个变量,那么使用变量声明列表是一种从 JS 文件中减少几个字节的简单方法。

    【讨论】:

      【解决方案4】:

      这似乎是过早的优化,万恶之源。

      它将执行多少次?这将消耗整个程序的哪一部分?

      【讨论】:

        【解决方案5】:

        我会用几个问题来反驳你关于性能的问题:

        1. 您是否注意到性能问题?
        2. 您确定您的 var 语句是瓶颈吗?
        3. 您是否测试过每个版本?

        我将假设所有这些的答案都是

        任何选项都不应该有任何显着差异,尽管唯一确定的方法是运行它们并进行测试。 JavaScript 作为一种异步客户端语言意味着您必须运行非常大量的代码才能使var 语句成为任何类型的瓶颈。


        最后,如果您决定使用哪个版本,我建议您使用不带赋值的单个 var 语句:

        function () {
            var a,
                b,
                c,
                foo,
                bar,
                fizz,
                buzz;
            a = 1;
            ...
            b = 3;
        }
        

        这样做的原因是,由于变量提升,这本质上是代码的执行方式。然后我可以移动初始化语句,以便首先使用变量,例如在for 循环中:

        function foo(arr) {
            var i,
                l;
            ...
            for (i = 0, l = arr.length; i < l; i++) {
                doStuff(arr[i]);
            }
            ...
        }
        

        【讨论】:

        • JavaScript 是完全同步的,而不是异步的。
        • @Wk_of_Angmar,你错过了重点。 JavaScript 在执行时是同步的,但是大部分代码是异步运行的。绝大多数时候,绝大多数 JavaScript 只是在等待浏览器告诉它发生了什么事,以便它可以执行百分之几毫秒。
        【解决方案6】:

        它们基本上都做同样的事情:声明一个变量并最终定义它(给它赋值)。您在整个示例中唯一要更改的是发生的顺序,甚至这取决于正在编译您的 JavaScript 的浏览器 - 有些可能会执行其他优化,而其他一些则不会。

        您应该遵循一些风格准则,this answer 很好地解释了它们。请记住,该答案与技术无关,可能根本不适用于 JavaScript。

        【讨论】:

          【解决方案7】:

          如果可能,请远离选项 1,无需进行两次分配。

          即使在 for 循环或其他复合语句/块中声明的变量也将在其包含块之外可用。

          你也可以这样做:

          function MyFunction() {
          
            var a = SomeValue, b = SomeVavlue2;
          
          }
          

          【讨论】:

            猜你喜欢
            • 2015-03-28
            • 1970-01-01
            • 1970-01-01
            • 2014-05-12
            • 2011-03-29
            • 1970-01-01
            • 2022-10-07
            • 2010-12-13
            • 1970-01-01
            相关资源
            最近更新 更多