【问题标题】:best-practice on for loop's conditionfor循环条件的最佳实践
【发布时间】:2011-02-23 22:47:11
【问题描述】:

在这种情况下什么被认为是最佳实践?

for (i=0; i<array.length(); ++i)

for (i=array.length()-1; i>=0; --i)

假设我不想从某个方向迭代,而是在数组的裸露长度上进行迭代。另外,我不打算改变循环体中数组的大小。

那么,array.length() 会在编译期间保持不变吗?如果没有,那么第二种方法应该是要采用的方法..

【问题讨论】:

  • 您弄错版本 2 的事实说明了一些问题。不是吗?
  • 这也取决于语言。如果i 未签名,您将无法在向下计数版本中正确获取终止条件。 (即使i已签名,也已经错了。)
  • 不会 ++i 导致最后一次传球越界吗?
  • 前/后增量在 for 循环中无关紧要,因为当流控制到达结束大括号时它会自行执行。 ++i 之间没有区别(带整数);和我++;在代码中单独一行。类和前/后增量和复制构造函数可能有所不同,所以要小心。

标签: for-loop compilation compile-time


【解决方案1】:

for (i=0; i&lt;array.length(); ++i) 对我来说更好,但for (i=array.length()-1; i&gt;=0; --i) 最快,因为与 0 相比,与两个 varbiales 相比,普通处理器检查条件最快。

array.lenght() 是常量,如果您不在迭代中从该数组中添加/删除元素。

【讨论】:

  • 最快取决于所使用的语言
  • 如果您正在访问零索引数组中的项目,您实际上需要for (i = array.length() - 1; i &gt;= 0; --i)
  • @Jeff 你能详细说明一下吗?哪些语言(例如)不会因为选择另一种语言而烦恼?
【解决方案2】:

版本 2 已损坏,将从数组的过去一端迭代到 1。(现已更正)

坚持使用第 1 版。它得到了很好的认可,不会让读者产生双重印象。

【讨论】:

  • 根据语言的不同,版本 2 仍然可以被破坏!例如,当 array.Length 为 0 并且 i 是无符号整数时。经典整数下溢。
【解决方案3】:

我会使用第一种方法,因为它更具可读性,而且我可以查看并看到您正在遍历循环。第二个花了我一秒钟:(。

array.length 将保持不变,只要您不修改数组。

【讨论】:

    【解决方案4】:

    版本 1 使用更广泛,更易于理解。如果编译器不将 array.length() 优化为常量,版本 2 有时可能会稍微快一些,但是...insert your own premature optimization comment here

    编辑:至于 array.length() 是否会被优化,这取决于语言。如果语言使用数组作为“普通”对象或数组可以动态调整大小,那么它只是一个方法调用,编译器不能假设会返回一致的返回值。但是对于数组是特殊情况或对象的语言(或者编译器真的很聪明......),速度差异可能会被消除。

    【讨论】:

    • +1 提及过早优化。最清晰的方法是最好的方法,直到发现它会导致问题。
    • 但是array.length() 无法知道给定动态大小的数组
    【解决方案5】:

    在大多数情况下,我希望 array.length() 以 O(1) 的方式实现,因此它不会真正影响循环的性能。如果您有疑问,或者想确保它是一个常量,请明确地这样做:

    // JavaScript
    var l = a.length;
    
    for (var i=0; i<l; i++) {
      // do something
    }
    

    我认为反向表示法属于过早优化类别的“聪明的技巧”。它更难阅读,更容易出错,并且与我建议的替代方案相比并没有真正提供好处。

    但是由于编译器/解释器的实现有很大的不同,而且你没有说你指的是什么语言,所以很难对此做出绝对的陈述。我会说除非这是在代码的绝对时间关键部分或以其他方式对代码运行时间有可衡量的贡献,并且您的基准测试表明以不同的方式进行操作会带来真正的好处,否则我会坚持使用更易于理解和维护的代码.

    【讨论】:

      【解决方案6】:

      对于我自己的代码中的 for 循环,虽然它可能有点矫枉过正,但我​​很早就养成了编写循环的习惯,使得长度只计算一次,但循环以自然的方式进行:

      int len = array.length();
      for (int i=0; i<len; ++i) {
          doSomething(array[i]);
      }
      

      不过,现在我更喜欢使用“for-each”设施,因为它们可用且方便;它们使循环更容易阅读和万无一失。在 C++ 中会是这样的:

      std::for_each(array.begin(), array.end(), &doSomething);
      

      【讨论】:

        【解决方案7】:

        版本 1 最快。对于 (i=0; 我

        【讨论】:

          猜你喜欢
          • 2018-09-23
          • 2012-09-20
          • 1970-01-01
          • 2013-04-10
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2014-11-25
          相关资源
          最近更新 更多