Java的+ =, – =,* =,/ =复合赋值运算符
直到今天,我认为,例如:
i += j;
只是一个捷径:
i = i + j;
但是,如果我们尝试这样做:
int i = 5; long j = 8;
那么i = i + j;
不会编译,但i += j;
将编译好。
这是否意味着其实i += j;
是这样一个快捷方式i = (type of i) (i + j)
?
和往常一样,JLS有这个答案。 在这种情况下, §15.26.2复合赋值运算符 。 摘录:
E1 op= E2
的复合赋值expression式相当于E1 = (T)((E1) op (E2))
,其中T
是E1
的types,只是E1
只被计算一次。
从§15.26.2引用的一个例子
以下代码是正确的:
short x = 3; x += 4.6;
并导致x的值为7,因为它相当于:
short x = 3; x = (short)(x + 4.6);
换句话说,你的假设是正确的。
这个演员的一个很好的例子是使用* =或/ =
byte b = 10; b *= 5.7; System.out.println(b); // prints 57
要么
byte b = 100; b /= 2.5; System.out.println(b); // prints 40
要么
char ch = '0'; ch *= 1.1; System.out.println(ch); // prints '4'
要么
char ch = 'A'; ch *= 1.5; System.out.println(ch); // prints 'a'
很好的问题。 Java语言规范确认您的build议。
例如,下面的代码是正确的:
short x = 3; x += 4.6;
并导致x的值为7,因为它相当于:
short x = 3; x = (short)(x + 4.6);
是,
基本上当我们写
i += l;
编译器将其转换为
i = (int)(i + l);
我刚刚检查了.class
文件的代码。
真的是一件很好的事情要知道
你需要explicitly
从long
为int
,如果是i = i + l
那么它会编译并输出正确的结果。 喜欢
i = i + (int)l;
要么
i = (int)((long)i + l); // this is what happens in case of += , dont need (long) casting since upper casting is done implicitly.
但在+=
情况下,它正常工作,因为运算符隐式地执行从右variablestypes到左variablestypes的types转换,因此不需要显式转换。
这里的问题涉及types转换。
当你添加int和long时,
- int对象被铸造得很长,两者都被添加,你得到长的对象。
- 但长的对象不能被隐式地转换为int。 所以,你必须明确地做到这一点。
但是+=
是以这样一种方式进行编码的,即它可以进行types转换。 i=(int)(i+m)
在Java中,当赋值操作右侧的expression式types可以安全地升级到赋值左侧的variablestypes时,将自动执行转换。 因此我们可以安全地分配:
byte - > short - > int - > long - > float - > double。
反过来也不行。 例如,我们不能自动将long转换为int,因为第一个需要比第二个更多的存储,因此信息可能会丢失。 为了强制这种转换,我们必须进行明确的转换。
types – 转换
有时候,面试中可能会提出这样一个问题。
例如,当你写:
int a = 2; long b = 3; a = a + b;
没有自动types转换。 在C ++中,编译上述代码不会有任何错误,但是在Java中,您将得到类似Incompatible type exception
。
所以要避免它,你必须写下你的代码:
int a = 2; long b = 3; a += b;// No compilation error or any exception due to the auto typecasting
主要区别在于, a = a + b
没有types转换,所以编译器因为没有types转换而生气。 但是, a += b
,它真正在做的是将b
types转换为与a
兼容的types。 所以,如果你这样做
int a=5; long b=10; a+=b; System.out.println(a);
你真正做的是:
int a=5; long b=10; a=a+(int)b; System.out.println(a);
微妙点在这里…
当'j'是双精度时'i + j'有一个隐式types转换,而'i'是一个inttypes。 当它们之间有一个操作时,Java 总是把一个整数转换成一个double。
澄清'i + = j',其中i是一个整数,j是一个double,可以描述为
i = <int>(<double>i + j)
请参阅: 隐式转换的描述
在这种情况下,为了清晰起见,您可能需要将j
转换为(int)
。
在复合赋值运算符的情况下,将自动执行内部types转换:
byte b1 = 10; //b1 = b1 + 1; Compile time error because found int System.out.println(b1); byte b3 = 10; b3 += 1; //in compound assignment implicit type casting will be performed simultaneously System.out.println("b3=: "+b3); byte b4 = 127; b4 += 3; //in compound assignment implicit type casting will be performed simultaneously System.out.println("b4=: "+b4);//-126
在某些情况下,您将失去一些价值:
int i = 1; i += 1.5; System.out.println("i=: "+i); //will print 2, and you lost .5 !!!