使用带有%d的printf作为格式说明符并将float作为参数,例如2.345,它打印1546188227.因此,我知道这可能是由于单点浮点精度格式转换为简单的十进制格式。但是当我们用%d作为格式说明符打印2.000时,为什么它只打印0? 请帮忙。
答案 0 :(得分:4)
格式说明符%d
只能用于int
类型(和兼容类型)的值。尝试将%d
与float
或任何其他类型一起使用会产生未定义的行为。这是真正适用的唯一解释。从语言的角度来看,您看到的输出基本上是随机的。而且你不能保证得到任何输出。
如果您仍然有兴趣调查您看到的输出的具体原因(无论它有多少意义),您将不得不执行特定于平台的调查,因为实际行为主要取决于各种实现细节。你甚至没有在帖子中提到你的平台。
在任何情况下,作为旁注,请注意,不可能将float
值作为可变参数传递给可变参数函数。在这种情况下,float
值始终转换为double
并传递为double
。因此,在您的情况下,您尝试打印的值为double
。但行为仍未定义。
答案 1 :(得分:1)
转到here,输入2.345
,点击“四舍五入”。观察64位十六进制值:4002C28F5C28F5C3
。请注意1546188227
为0x5c28f5c3
。
现在重复2.00。观察到64位十六进制值为4000000000000000
P.S。当你说你给出一个 float 参数时,你的意思是你给出了一个 double 参数。
答案 2 :(得分:1)
ISO / IEC 9899:1999标准7.19.6规定:
If a conversion specification is invalid, the behavior is undefined.239)
If any argument is not the correct type for the corresponding conversion
specification, the behavior is undefined.
答案 3 :(得分:0)
如果您正在尝试使其打印整数值,请在调用中将浮点数转换为整数:
printf("ints: %d %d", (int) 2.345, (int) 2.000);
否则,请使用浮点格式标识符:
printf("floats: %f %f", 2.345, 2.000);
答案 4 :(得分:0)
当您使用具有错误格式说明符的printf作为相应参数时,结果是未定义的行为。它可以是任何东西,可能因实现而异。只有正确使用指定的格式才能定义行为。
答案 5 :(得分:0)
首先是一个小的挑剔:文字2.345实际上是double类型,而不是float,而且,当用作函数的参数时,甚至浮点数(如文字2.345f)也会被转换为double可变数量的参数,例如printf。
但这里发生的是,double值的(通常)64位被发送到printf,然后它(通常)将这些位中的32位解释为整数值。所以恰好这些位是零。
根据标准,这就是所谓的未定义行为:允许编译器做任何事情。