参考博客:一看就懂的i++和++i详解
    我们知道i++是先自增,然后返回自增之前的值,++i是先自增然后返回自增之后的值
    代码如下:

    1. int i = 0;
    2. int a = 0;
    3. a = i++; //i赋值给a,然后自己加一,此时a=0,i=1;
    4. System.out.println(a);
    5. a = ++i; //i自己加一,然后赋给a,此时a=2,i=2;
    6. System.out.println(a);

    输出结果:

    0 2

    class文件如下:

    1. int i = 0;
    2. int a = false;
    3. int i = i + 1;
    4. System.out.println(i);
    5. ++i;
    6. System.out.println(i);

    下面看i=i++这种情况

    1. int i = 0;
    2. int a = 0;
    3. i = i++;
    4. i = i++;
    5. System.out.println(i);

    运行结果:

    0

    class文件:

    1. int i = 0;
    2. int a = false;
    3. byte var10000 = i;
    4. int var3 = i + 1;
    5. i = var10000;
    6. var10000 = i;
    7. var3 = i + 1;
    8. i = var10000;
    9. System.out.println(i);

    我们发现,一开始用var10000把i保存了下来,然后i+1,又用一个新的变量var3保存了下来,然后又把i之前的值赋给了i,这样一来,i又变回去了。

    我们把i = i++改成i = ++i试试

    1. int i = 0;
    2. int a = 0;
    3. i = ++i;
    4. System.out.println(i);

    输出结果:

    1

    class文件:

    1. int i = 0;
    2. int a = false;
    3. int i = i + 1;
    4. System.out.println(i);

    可以发现,这次i变成了1

    原因:
    i=i++的字节码指令如下

    0: iconst_0 // 生成整数0 1: istore_1 // 将整数0赋值给1号存储单元(即变量i,i=0) 2: iload_1 // 将1号存储单元的值加载到数据栈(此时 i=0,栈顶值为0)

    3: iinc 1, 1 // 号存储单元的值+1(此时 i=1)

    6: istore_1 // 将数据栈顶的值(0)取出来赋值给1号存储单元(即变量i,此时i=0)

    7: getstatic #16 // 下面是打印到控制台指令

    10: new #22

    13: dup

    14: ldc #24

    16: invokespecial #26

    19: iload_1

    20: invokevirtual #29

    23: invokevirtual #33

    26: invokevirtual #37

    29: return

    从编码指令可以看出,i被栈顶值所覆盖,导致最终i的值仍然是i的初始值。无论重复多少次i = i++操作,最终i的值都是其初始值。
    简单说就是,i本来是0,执行i++之后,i变成了1,但是返回的是自增之前的数据,所以i又变成了0。