在Java中,

有整数类型(char/short/int/long/byte)

有 float 类型(float/double)

与C语言不同,它是 boolean 类型(boolean),而不是整数类型。

问题1)

是否有通用的转换规则(按照JLS),哪种类型可以转换为另一种类型?出于常识,我知道不允许将整数和浮点类型强制转换为boolean
问题2)

请帮助我了解以下输出的原因:

        /*
         * Casting rules for primitive types
         */
        double aDoubleValue = 30000000000000000000.123438934;
        int doubleToInt = (int)aDoubleValue; //stores max value 2147483647, makes sense!!
        byte doubleToByte = (byte)aDoubleValue; //stores -1, why not 127?
        short doubleToShort = (short)aDoubleValue; // stores -1, why not 32767?
        long doubleToLong = (long)aDoubleValue; // stores 9223372036854775807, makes sense!!
        float doubleToFloat = (float)aDoubleValue; // stores 3.0E19, 3.0 x 10^19  max value of float
        char doubleToChar = (char)aDoubleValue; // what does this store?

最佳答案

JLS lists


  • 字节为short,int,long,float或double
  • 短到int,long,float或double的
  • char转换为int,long,float或double
  • int转换为long,float或double
  • 长时间 float 或加倍
  • float 为双

  • 其他所有内容都需要显式转换。 Narrowing比较复杂:
  • doublefloat使用标准IEEE 754舍入。
  • 整数值的最高有效位被剥离为目标类型的可用宽度。这可能会导致出现符号位,例如(byte)0xfff == (byte)-1;
  • 如果源类型为浮点,而目标类型为long,则将值四舍五入为整数。
  • 如果源类型为浮点,而目标类型为整数而不是long,则首先通过四舍五入将值转换为int。然后,使用整数转换将生成的int转换为目标类型。

  • 例子:
    int doubleToInt = (int)aDoubleValue;
    

    根据四舍五入规则产生Integer.MAX_VALUE
    byte doubleToByte = (byte)aDoubleValue;
    

    首先将其转换为int,产生Integer.MAX_VALUE,然后将其转换为byteInteger.MAX_VALUE0x7fffffff,因此字节值0xff-1
    short doubleToShort = (short)aDoubleValue;
    

    再次相同:转换为int,产生Integer.MAX_VALUE0x7fffffffshort会产生0xffff,即-1

    棘手的事情实际上是tochar转换。 char是一个单一的16位unicode字符,因此char doubleToChar = (char)aDoubleValue通过现在熟悉的规则为您提供'\uffff'

    可以看出,浮点运算和整数变窄运算之间存在差异。浮点运算进行实际舍入,而整数运算执行按位钳位。

    整数语义可能是从C继承的。至少从浮点到整数的缩小操作的第一步也是您所期望的。从double/float到short,byte和char的第二个缩小步骤似乎有点令人惊讶,但是如果您真的将float转换为short,则可能应该仔细检查一下您是否知道自己在做什么。

    09-10 04:41
    查看更多