++ i或i ++ in for循环?

Ism*_*ush 54 c++ for-loop pre-increment post-increment

可能重复:
在C++中i ++和++ i之间是否存在性能差异?

是否有一些程序员++i在正常的for循环中写入而不是写入i++

Dre*_*all 109

++i 由于它的语义,它的效率稍高:

++i;  // Fetch i, increment it, and return it
i++;  // Fetch i, copy it, increment i, return copy
Run Code Online (Sandbox Code Playgroud)

对于类似int的索引,效率增益最小(如果有的话).对于迭代器和其他较重的对象,避免该副本可能是一个真正的胜利(特别是如果循环体不包含太多工作).

作为一个例子,考虑以下循环使用理论上的BigInteger类提供任意精度整数(因此某种类似矢量的内部):

std::vector<BigInteger> vec;
for (BigInteger i = 0; i < 99999999L; i++) {
  vec.push_back(i);
}
Run Code Online (Sandbox Code Playgroud)

i ++操作包括一个循环的复制构造(即操作符新的,逐位复制)和销毁(操作符删除),这个循环除了基本上再复制一个索引对象之外什么都不做.从本质上讲,你只需要使用后缀增量就可以完成的工作量增加一倍(并且最有可能增加内存碎片),前缀就足够了.

  • 我想提出你的答案但不会再评价为42 (4认同)

Oli*_*rth 84

对于整数,前后增量之间没有区别.

如果i是非平凡类的对象,则++i通常是首选,因为对象被修改然后被评估,而i++在评估之后修改,因此需要进行复制.

  • 虽然使用整数生成相同的代码,但由于第二段,对于所有类型使用`++ i`可能是个好主意,因此您习惯将它用于所有类型. (18认同)
  • @Jim:编译器必须调用相关的运算符重载(`operator ++()`或`operator ++(int)`分别用于preincrement和postincrement).如果它们实际上是等效的,并且如果内联调用,并且所涉及的副本全部被优化器删除,那么发出的代码可能会相同 - 尝试它.但是编译器肯定不能仅仅基于结果未使用而替换另一个.我并不特别在意,因为为了清晰起见我写了`++ i`(因为我认为它)."增量i" - >"++ i". (4认同)
  • @Token:我原则上同意.但是,`i ++'在C代码中有些惯用; 如果你经常使用这两种语言,它会让人感到困惑...... (2认同)
  • @Jim Mischel:编译器可以看到返回值没有被使用,但它没有理由期望 ++i 和 i++ 对副本具有相同的语义。所以它必须调用程序员要求的版本。 (2认同)

Ric*_*ard 8

++i是一个预增量; i++是后增量.
后增量的缺点是它会产生额外的值; 它在修改时返回旧值的副本i.因此,你应该尽可能避免它.


bgp*_*ter 5

对于整数,这是首选。

如果循环变量是一个类/对象,它可能会产生影响(只有分析才能告诉您它是否有显着差异),因为后增量版本要求您创建该对象的副本并被丢弃。

如果创建该副本是一项昂贵的操作,那么您每次执行循环时都需要支付一次该费用,根本没有任何原因。

如果您养成了始终使用 in for 循环的习惯++i,则无需停下来思考在这种特定情况下所做的事情是否有意义。你总是这样。