按照我的理解,投射用于将值从一种类型转换为另一种类型。这个程序连续使用三个演员。连续多次投射不按预期工作
public class Multicast {
public static void main(String[] args) {
System.out.println((int) (char) (byte) -1);
}
}
我以为它会打印-1,但它打印它打印65535,但为什么?
按照我的理解,投射用于将值从一种类型转换为另一种类型。这个程序连续使用三个演员。连续多次投射不按预期工作
public class Multicast {
public static void main(String[] args) {
System.out.println((int) (char) (byte) -1);
}
}
我以为它会打印-1,但它打印它打印65535,但为什么?
java中的char是一个无符号的16位整数。如果您将一个负整数文字(如-1)转换为char,则该值将被解释为正数;在这种情况下是65535-或Unicode字符\ uFFBF。
检查这个-1投仅焦炭,
System.out.println((char) -1);
如果与int
或byte
类型转换,这只是返回-1
。
表达:(int) (char) (byte) -1
-1
是int类型(byte) -1
是具有值-1(char) (byte) -1
首先将具有值字节的一个字节-1是符号扩展再次是一个32位的整数值-1。这意味着所有的32位都被设置为1(32位中的-1的二补码)。然后它被转换为类型为char
,这是一个无符号的16位值,所以你得到的16位设置为1,其值为65535.(int) (char) (byte) -1
通过明确地将其重新转换为32位整数,确保它被打印为一个数字,而不是代码点为65535的字符。从字节到字符的转换比较棘手,因为字节是带符号的类型和charunsigned。在保留数值的同时,通常可以从一种整数类型转换为较宽的类型,但不可能将一个负的字节值表示为char。因此,从字节到charis的转换不被视为扩展原始转换[JLS 5.1.2],而是扩展和缩小基元转换[JLS 5.1.4]:将字节转换为int并将int转换为char。
如果原始值的类型被签名,则执行符号扩展;零扩展如果它是一个字符,不管它正在被转换的类型为 。
因为byte是一个有符号类型,所以在将bytevalue -1转换为char时会发生符号扩展。由此产生的charvalue全部设置了16位,所以它等于2增加到16-1或65,535。来自charto int的强制转换也是一个扩展原始转换,因此该规则告诉我们执行了零扩展而不是符号扩展。
生成的int值是65535,这正是程序打印的内容。
已经很详细地回答了http://stackoverflow.com/questions/24635977/why-does-intcharbyte-2-produce-65534-in-java – Ramanlfc