Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/321.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
在Java中,float(内存为4字节)可以保存long(内存为8字节)值。怎样?_Java_Long Integer - Fatal编程技术网

在Java中,float(内存为4字节)可以保存long(内存为8字节)值。怎样?

在Java中,float(内存为4字节)可以保存long(内存为8字节)值。怎样?,java,long-integer,Java,Long Integer,下面是代码片段 请告诉我,这种使用小内存区域保存大数据的算法是什么 public static void main(String[] args) { long longValue = 2147483649L;//which is 8bytes in memory float floatValue = 23f;//which is 4bytes in memory floatValue = longValue; System.out.println(floatVal

下面是代码片段

请告诉我,这种使用小内存区域保存大数据的算法是什么

public static void main(String[] args) {
    long longValue = 2147483649L;//which is 8bytes in memory
    float floatValue = 23f;//which is 4bytes in memory
    floatValue = longValue;
    System.out.println(floatValue);
}

答案是
float
可以保存一些
long
值。如果它适合于
浮点
浮点表示形式。其他数字将失去精度或转换为不同的数字

请参见此示例:

long l = Integer.MAX_VALUE;
System.out.println(l); // Prints 2147483647

float f = l;
System.out.printf("%f", f); // Prints 2147483648.000000
如您所见,将2147483647转换为
float
lost-precision(成为一个“不同”的数字)。尽管“测试”数字明显适合4字节(即使使用有符号表示),但它不能适合4字节
浮点
表示(它还使用一些位,例如指数)

浮点数使用标准表示。

请尝试运行以下代码:

    long longValue = Long.MIN_VALUE + 1; // which is 8bytes in memory
    float floatValue = longValue; // which is 4bytes in memory
    System.out.println(longValue + " != " + (long) floatValue);
它将打印:
-9223372036854775807!=-9223372036854775808

浮点(和双精度)可以存储任何值(甚至无穷大),但值越大,保存的精度越低,因为它确实保存在有限的空间中

例如,请尝试:

    float floatValue = (float) 9999999999999999999999999999999999999999999999999999999.9;
    System.out.println(floatValue);
它将打印
无限

或者这个:

    float floatValue = (float)   9999999999999999999999999999990d;
    float floatValue2 = (float) 10000000000000000000000000000000d;
    System.out.println(floatValue + " = " + floatValue2);
将打印:

1.0E31 = 1.0E31
这里的关键是数字的精度。中的32位浮点数可以采用非常大和非常小的值:

±1.18×10−38至±3.4×1038
精度:约7位小数

这些大的和小的数字通过将数字拆分为尾数和指数来表示。尾数是存储“实际数字”的部分(而指数只存储“数字有多大”。32位浮点值的尾数有23位

这意味着,当长值变得太大(即,大于可用23位表示的值)时,两个不同的
long
值将转换为相同的
float

这可以通过以下程序快速(令人信服地)进行检查:

public class LongAsFloat
{
    public static void main(String[] args)
    {
        float previousFloatValue = 0;
        for (long i=1; i<Long.MAX_VALUE; i++)
        {
            float floatValue = i;

            if (floatValue == previousFloatValue)
            {
                System.out.println("Got "+floatValue+" for "+i+" and "+(i-1));
                break;
            }
            previousFloatValue = floatValue;
            if (i % 10000L == 0)
            {
                System.out.println("Checking "+i);
            }
        }
    }
}

并非巧合,224=16777216-太大了,无法用23位表示。

你可以给一个浮点赋值一个long,但你会失去精度这个问题有一个Java难题-它试图使用浮点循环,看,循环永远循环(因为跳过了数字,或者当
f+1==f
且浮点保持不变时效果更好)。
Got 1.6777216E7 for 16777217 and 16777216