3
#include <stdio.h>
int main(void){
    float a = 1.1;
    double b = 1.1;
    if(a == b){
        printf("if block");
    }
    else{
        printf("else block");
    }
    return 0;
}

打印:否则阻止

#include <stdio.h>
int main(void){
    float a = 1.5;
    double b = 1.5;
    if(a == b){
        printf("if block");
    }
    else{
        printf("else block");
    }
    return 0;
}

打印:如果块

这背后的逻辑是什么?

使用的编译器:gcc-4.3.4

4

3 回答 3

6

这是因为1.1不能完全用二进制浮点表示。但是1.5是。

因此,floatdouble表示将持有略有不同的 值1.1

这正是写成二进制浮点时的区别:

(float) 1.1 = (0.00011001100110011001101)₂
(double)1.1 = (0.0001100110011001100110011001100110011001100110011010)₂

因此,当您比较它们(并且float版本得到提升)时,它们将不相等。

于 2012-01-26T05:36:18.143 回答
4

必读:每个计算机科学家都应该知道的关于浮点运算的知识

于 2012-01-26T05:34:24.837 回答
1

二进制中十进制 1.1 的确切值是无尾小数 1.00011001100110011001100(1100).... 双精度常数是该尾数1.1的 53 位截断/近似值。现在,当转换为浮点数时,尾数将仅以24位表示。

float转换回双精度时,尾数现在恢复为 53 位,但所有超过 24 位的数字的内存都丢失了 - 该值是零扩展的,现在您正在比较(例如,取决于舍入行为)

1.0001100110011001100110011001100110011001100110011001

1.0001100110011001100110000000000000000000000000000000

现在,如果您使用 1.5 而不是 1.1;

十进制的 1.5 正好是二进制的 1.1。它可以精确地以2位尾数表示,因此即使是 24 位浮点数也很夸张......你所拥有的是

1.1000000000000000000000000000000000000000000000000000

1.10000000000000000000000

后者,零扩展到双倍将是

1.1000000000000000000000000000000000000000000000000000

这显然是同一个数字。

于 2017-08-19T12:28:30.243 回答