【问题标题】:Optimization? `i--` vs. `i++`优化? `i--` 与 `i++`
【发布时间】:2012-07-29 09:47:43
【问题描述】:

当循环结构引起我的注意时,我正在浏览一些 JavaScript 代码。它并没有什么特别的地方,而是以一种与我不同的方式进行迭代。当我需要循环一些不依赖于顺序的东西时,我通常会数数,从头到尾迭代,如下所示:

do
{
    // I feel like I'm going in circles
    i++;
} while (i < length)

但是,这个 JavaScript 函数倒计时,从头到尾循环。

var i = data.length - 1;
if(i >= 0)
{                   
    do
    {
        // Around and around, we go                     
    }while(i--)
}

向下计数有什么好处还是只取决于开发人员的偏好?

【问题讨论】:

  • 顺便说一句,有没有办法防止“--”变成破折号?
  • 如果您想进一步优化,还可以查看Duff's Device。它减少了您必须执行的比较次数(最常见的是 8 倍)。

标签: optimization loops


【解决方案1】:

可能不会。开发人员很可能只是想倒数。

但是,标准的 0 到长度 1 循环并不总是理想的。例如,在特定的缓存架构下,无论出于何种原因,反向访问结构的元素可能会更快。我想不出在 JavaScript 中会发生这种情况的任何合理情况,但它确实发生在基于应用程序的语言中,尤其是像 C 这样的相对低级的语言。

【讨论】:

    【解决方案2】:

    如果你正在从数组中删除东西,倒退会更好。

    假设您有一个包含 10 个事物的数组,并且您最终希望通过在循环期间执行的一些条件来删除索引 3 和 4 处的项目。你正在增加你的计数器。当您在 3 处移除时,阵列相对于计数器会发生什么情况?数组长度缩小到 9,索引 4 处的内容现在位于索引 3,并且您将计数器增加到 4。您只是跳过了要删除的内容。如果你倒退,你可以避免这个问题。

    另外,going backwards is faster,因为处理器将索引与 0 进行比较比将索引与随机数进行比较的速度更快。

    【讨论】:

    • 更糟糕的是 - 如果迭代动态数组集合并删除一些对象,向上计数将导致超出数组末尾。倒计时就好了。
    【解决方案3】:

    引用类似的 SO 问题/答案:

    因为您的转发条件必须接收长度属性 每次你的数组,而其他条件只需要检查 “大于零”,一个非常快的任务。

    Loop Iteration - Bergi

    【讨论】:

      【解决方案4】:

      嗯。理论上不,循环使用 for 或使用 while 应该没有区别,但这是我的 2 美分。 查看是否存在差异的唯一方法是进行性能测试,一个使用while,另一个使用for,比如说100万个元素,计算执行时间并自己看看。 循环有很多优化技术(无论是 for 还是 while),最常见的一种是在一个循环中进行多次迭代。例子: for 循环的标准是:

      var i;
      for (i=0;i < N; i++) {
          bla();
      }
      

      现在我们通过在每次迭代中执行相同的多次来优化这一点

      var i;
          for (i=0;i < N; i+=5) {
              if (i < N-5) {
                bla();
                bla();
                bla();
                bla();
                bla();
              }
          }
      for (j=i; j <N;j++){
        bla();
      }
      

      这种方式保证了更少的迭代次数。根据您每次迭代的操作以及数组/堆栈的大小,它可以提供更好的性能。有很多关于如何提高循环性能的文章

      【讨论】:

        【解决方案5】:

        我看到至少一项研究表明,递减的 while 循环是在 JavaScript 中执行循环的最快方法:https://blogs.oracle.com/greimer/entry/best_way_to_code_a

        请注意,这是针对研究中的 JavaScript 引擎的,其他语言/机器实现可能会提供不同的结果。例如,在 C 语言中,优化编译器可能会完全展开您的循环,并且生成的代码根本不会循环。

        【讨论】:

          猜你喜欢
          • 2017-03-30
          • 1970-01-01
          • 1970-01-01
          • 2011-10-31
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多