本文主要介绍 Java 中的++ii++ 的区别。

概念

在 Java 中,自增是一种非常常见的操作。其中包含两种写法:一种是 ++i 称为前递增运算符(前缀自增),另一种 ++i 称为后递增运算符(后缀自增)。顾名思义,前递增运算符在使用前递增变量,而后递增运算符在使用后递增变量。也属于一元运算符范畴。

作用

增量运算符通常在循环中使用,以自动执行循环迭代。

public static void main(String[] args) {
	
		int[] arr = {1, 2, 3, 4, 5};
		
		System.out.println("循环使用i++: ");				 
		for (int i = 0; i < arr.length; i++) {
			System.out.println(arr[i] + " ");
		}
		System.out.println("================");
		System.out.println("循环使用++i: ");
		for (int i = 0; i < arr.length; ++i) {
			System.out.println(arr[i] + " ");
		}
	}

运行结果:

i 在java中 java中+i+是什么意思_i 在java中

可见在for循环中,它们的使用没有明显区别。 

区别

(1)含义不同 

两者处理方式不同:++i 是从内存中加载 i,然后加1,再使用(赋值),最后存到内存中。而 i++ 是从内存中加载 i,使用(赋值),再加1,最后存到内存中。 

在下面示例中,我们可以清楚地看到i++与++i之间的区别。

public static void main(String[] args) {
		
		int a = 0;
		System.out.println(a++); // 0
		int b = 0;
		System.out.println(++b); // 1
	}

分析:对int a来说,我们对其应用i++形式自增,因为递增的操作在使用之后(这里指打印),所以a输出的是原值0;int b是在使用前执行自增,因此该变量输出的是1。

(2)性能差异

如前所述,这两种自增在某些情况下的性能是有差别的。原因在于++i 操作是变量本身加1返回,而 i++ 则是创建一个新变量,得到原有变量之后加1返回。因此,后缀自增的过程会创建一个新变量,在编译器没有优化的情况下,后缀自增的速度比前缀自增慢一点点。

代码测试:

public class OperatorTest04 {

	public static void main(String[] args) {	
	OperatorTest04 opt = new OperatorTest04(); 
	long maxIteration = 1000000000L;
	
	  System.out.println("<========== i++ 循环 ==========>");
	  long start = System.currentTimeMillis();
	  for (long i = 0; i < maxIteration; i++) {
	    opt.post();
	  }
	  System.out.println("后缀自增:" + ((System.currentTimeMillis()) - start) + "ms");
	  
	  System.out.println("<========== ++i 循环 ==========>");
	  long start2 = System.currentTimeMillis();
	  for (long i = 0; i < maxIteration; ++i) {
	    opt.pre();
	  }
	  System.out.println("前缀自增:" + ((System.currentTimeMillis()) - start2) + "ms");
	  
	  System.out.println("<========== 直接+1 循环 ==========>");
	  long start3 = System.currentTimeMillis();
	  for (long i = 0; i < maxIteration; ++i) {
	    opt.plusEquals();
	  }
	  System.out.println("加1赋值:" + ((System.currentTimeMillis()) - start3) + "ms");
	}
	
	private int post() {
	  int a = 0;
	  a++;
	  return a;
	}
	private int pre() {
	  int a = 0;
	  ++a;
	  return a;
	}
	private int plusEquals() {
	  int a = 0;
	  a += 1;
	  return a;
	}

}

运行结果:

i 在java中 java中+i+是什么意思_java_02

根据循环1000000000次后的时间来看,尽管每次运行的速度有细微差别,但是总体上++i自增比i++自增要快一点点,而加1赋值则相对不稳定。

总结

一般来说,经过优化的编译器,前缀自增和后缀自增在循环中应该会被编译成相同的字节码,不会有速度上的差异。为了保险起见,推荐写++i这种方式。