在for循环中,i++和++i有什么区别?

26

我刚开始学习Java,现在学习for循环语句。我不理解 ++ii++ 在for循环中的工作原理。

它们在加减法运算中如何工作?


许多现有的实例。简短回答:对于本地类型,没有区别。https://dev59.com/LXRB5IYBdhLWcg3w3K8J http://stackoverflow.com/questions/1941391/java-to-i-or-i-and-whats-the-difference-closed 和许多其他问题都来自http://stackoverflow.com/search?q=i%2B%2B+%2B%2Bi - dmckee --- ex-moderator kitten
相关:https://dev59.com/LnI-5IYBdhLWcg3woJ9J - jldupont
++i在理论上应该更有效率,因为i++仅包含一个++i和一个复制(以保存先前的值)。 但我猜JVM会在循环中优化后者(至少任何编译器都会这样做...)->没有区别。 - user3063349
7个回答

55

它们都会使数字增加。++i 相当于 i = i + 1

i++++i 很相似但并不完全相同。它们都会增加数字,但是 ++i 会在当前表达式被评估之前增加数字,而 i++ 则是在表达式评估后增加数字。

int i = 3;
int a = i++; // a = 3, i = 4
int b = ++a; // b = 4, a = 4

14
在典型的“for”循环用法上,它们基本相同。然而,要回答实际问题。 - Amber
小题大做:i = i + 1 是一个表达式,其值比 i 的初始值多一,这使它更像 ++i - Tom Hawtin - tackline

44

这是一个示例类:

public class Increment
{
    public static void main(String [] args)
    {
        for (int i = 0; i < args.length; ++i)
        {
            System.out.println(args[i]);
        }
    }
}

如果我使用javap.exe反汇编这个类,我会得到以下结果:

Compiled from "Increment.java"
public class Increment extends java.lang.Object{
public Increment();
  Code:
   0:   aload_0
   1:   invokespecial   #1; //Method java/lang/Object."<init>":()V
   4:   return

public static void main(java.lang.String[]);
  Code:
   0:   iconst_0
   1:   istore_1
   2:   iload_1
   3:   aload_0
   4:   arraylength
   5:   if_icmpge       23
   8:   getstatic       #2; //Field java/lang/System.out:Ljava/io/PrintStream;
   11:  aload_0
   12:  iload_1
   13:  aaload
   14:  invokevirtual   #3; //Method java/io/PrintStream.println:(Ljava/lang/String;)V
   17:  iinc    1, 1
   20:  goto    2
   23:  return

}

如果我将循环更改为使用i++,然后再次反汇编,我会得到以下结果:

Compiled from "Increment.java"
public class Increment extends java.lang.Object{
public Increment();
  Code:
   0:   aload_0
   1:   invokespecial   #1; //Method java/lang/Object."<init>":()V
   4:   return

public static void main(java.lang.String[]);
  Code:
   0:   iconst_0
   1:   istore_1
   2:   iload_1
   3:   aload_0
   4:   arraylength
   5:   if_icmpge       23
   8:   getstatic       #2; //Field java/lang/System.out:Ljava/io/PrintStream;
   11:  aload_0
   12:  iload_1
   13:  aaload
   14:  invokevirtual   #3; //Method java/io/PrintStream.println:(Ljava/lang/String;)V
   17:  iinc    1, 1
   20:  goto    2
   23:  return

}

当我比较这两个时,TextPad告诉我它们是相同的。

这意味着从生成的字节码的角度来看,在循环中使用++i和i++没有区别。在其他情况下,++i和i++会有所不同,但对于循环而言则不会。


9
为您付出额外的努力点赞。 - paxdiablo
不是循环本身在起作用,而是因为它没有处于更大的表达式上下文中。如果你的循环结束表达式更复杂,那么它可能会有所不同。 - Carl Norum
我会在循环示例中添加更多内容并再次尝试。 - duffymo
这个答案绝对值得加1!虽然在某些情况下会有所不同,比如:"for (int i = 0, int j = 0; i < args.length; j += ++i)" 和 "for (int i = 0, int j = 0; i < args.length; j += i++)"。 - BlondCode

20

它们都会将变量 i 增加一。就像是说 i = i + 1 。两者之间的区别微妙。如果你在循环中使用它们,那么没有区别:

for (int i = 0; i < 100; i++) {
}

for (int i = 0; i < 100; ++i) {
}

如果你想知道区别,请看这个例子:

int a = 0;
int b = a++; // b = 0; a = 1

a = 0;
b = ++a: // b = 1; a = 1

这个概念是,++a会将a的值加1并返回该值,而a++则是先返回a的值再将其加1。


7

for循环的处理方式如下:

1 首先进行初始化(i=0)

2 进行检查(i < n)

3 执行循环中的代码。

4 增加值

5 重复步骤2-4

这就是为什么在使用for循环时,i++和++i之间没有区别的原因。


这就是我在寻找的答案。谢谢! - Chris

5

区别在于后增量运算符i++返回递增前的i,而前增量运算符++i返回递增后的i。如果您询问典型的for循环:

for (i = 0; i < 10; i++)

或者

for (i = 0; i < 10; ++i)

它们完全相同,因为你没有将i++++i作为更大表达式的一部分。


3

i++++i 都是代表 i = i + 1 的简写。

除了改变 i 的值之外,它们还会返回 i 的值,具体是在加一之前(i++)或加一之后(++i)。

在循环中,第三个组件是每次迭代之后执行的代码。

for (int i=0; i<10; i++)

那部分的值没有被使用,因此上述内容与以下内容相同。
for(int i=0; i<10; i = i+1)

或者

for(int i=0; i<10; ++i)

在以下情况下,i++++i之间会有所不同:
while(i++ < 10)

for (int i=0; i++ < 10; )

看看TomH在David的回答中的迂腐,i=i+1与++i是相同的,而不是i++ :-) - paxdiablo

0

JLS§14.14.1, 基本的for语句明确指出ForUpdate表达式会被计算并且值会被丢弃。这样做的效果是使得两种形式在for语句的上下文中变得相同。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接