如果afloat的大小是4字节,那么它不应该能够容纳从8,388,607-8,388,608的数字,或者在那里的某个地方,因为我可能计算错了。
为什么f显示额外的15,因为f(0.1)的值仍然在8,388,607-8,388,608之间?

int main(int argc, const char * argv[])
{
    @autoreleasepool {
        float f = .1;
        printf("%lu", sizeof(float));
        printf("%.10f", f);
    }
    return 0;
}

2012-08-28 20:53:38.537 prog[841:403] 4
2012-08-28 20:53:38.539 prog[841:403] 0.1000000015

最佳答案

-8,388,608 ... 8,388,607让我相信你认为浮点数使用的是2的补码,而不是2的补码。在任何情况下,你拥有的范围表示24位,而不是从4个字节得到的32位。
C中的float使用IEEE754表示,基本上有三个部分:
标志。
指数(有点像刻度)。
分数(数字的实际数字)。
你基本上得到了一定的精度(比如7个十进制数字),指数决定了你是用这些来表示0.000000001234567还是12345670000。
您在0.1结尾处获得这些额外数字的原因是,IEEE754中无法精确表示该数字。参见this answer一篇解释原因的论文。
只有通过在精度位数(即小数位数)内添加两个倒数的幂(如1/21/161/65536等)才能精确地表示数字,并可缩放。
例如,像0.5这样的数字是可以的,因为它是1/2。类似地,可以从0.81251/21/4构建1/16
不可能(至少在23位精度内)用2的逆幂来构建0.1,所以它给了你最接近的匹配。

关于objective-c - 浮点小数的精度?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/12169614/

10-08 23:12