Day02笔记

来源: https://blog.ximinghui.org/wiz/Day02笔记.htm

自动类型转换

取值范围较小的数据类型向取值范围较大的数据类型自动转换,同时目标数据类型需兼容原数据类型。

long l = 100;
double d = 2.5F;

强制类型转换

有精度损失和数据溢出风险。

int i = (int) 2.5;

自动类型提升

char、byte、short 在参与计算时会自动提升为 int 类型。

byte b1 = 10;
byte b2 = 20;
byte b3 = b1 + b2; // 编译错误,不兼容的类型:从int转换成byte可能会有损失。
注:JVM在字节码层面上支持的整数类型只有int和long,所有比int小的整数类型都会被提升为int来运算。

运算符

位运算符算术运算符关系运算符逻辑运算符赋值运算符
&+==&&=
|-!=||+=
^*<!-=
~/<= *=
<<%> /=
>>++>= %=
>>>-- <<=
>>=
&=
|=
^=

条件运算符(亦称三元运算、三目运算):
variable x = (expression) ? value if true : value if false

instanceof运算符(亦称instanceof关键字):
( Object reference variable ) instanceof (class/interface type)

javac编译器的常量优化机制

常量优化可以使 int 类型的数值或者表达式(不含变量,final修饰的变量除外)直接赋值给 byte、short、char 三种类型的变量,但只有满足“数值或表达式结果不超出欲赋值变量类型的取值范围”条件时编译器才会进行常量优化。

byte b = 100; // 常量优化正确写法。
short s = 100; // 常量优化正确写法。
char c = 200; // 常量优化正确写法。
byte b1 = 100 + 2; // 常量优化正确写法。
byte b2 = b + 2; // 编译错误:包含变量。
char c1 = 65536; // 编译错误:超出 char 取值范围。
注:常量不仅指字面量,也包括命名常量(named constant)。命名常量也可描述为“final修饰的变量”或“值不能发生改变的变量 ”,如Math类的PI。

命名常量的示例:

byte b;
final byte B1 = 10;
final byte B2 = 20;
b = B1 + B2; // 编译通过:命名常量优化

关于字符串字面量的优化见 Day08笔记.md

隐式类型转换

常量优化属于隐式类型转换的一种,如 byte b = 100 等效于 byte b = (byte) 100 。除了常量优化外,下述情况也属于隐式类型转换。

byte b = 127;
b = b + 1; // 本行代码编译不通过 ①
b++;       // 本行代码编译通过 ②
b += 1;    // 本行代码编译通过 ③

①: 等号右侧表达式中的b进行运算时会自动提升类型为int,由于b是变量而不是常量,故不满足常量优化条件,因此在将int值赋给byte变量时会发生错误——不兼容的类型。

② ③: 自加运算符(++)、自减运算符(--)和复合赋值运算符(如+=、-=、*=、/=等)均隐含强制类型转换,如代码中 “ b++ ” 和 “ b += 1 ” 等效于 “ b = (byte) (b+1) ”。

注:隐式类型转换需当心计算时数据溢出风险

参考:

  1. 15.26.2. Compound Assignment Operators - Oracle文档

Xi_Minghui
1 声望0 粉丝

一枚普普通通的程序猿