从float到double,以及从double到float会导致精度丢失吗?

12
float fv = orginal_value;  // original_value may be any float value
...
double dv = (double)fv;
...
fv = (float)dv;

fv是否应该与original_value完全相等?可能会丢失任何精度吗?


3
可能是重复的问题吗?https://dev59.com/oHA75IYBdhLWcg3wDUgo - Pumkko
1
感谢您的评论。我认为情况有所不同。问题的后端是:我想将一个32位浮点数值存储到double(64位)中以简化操作,但在一些过程之后,从存储的double值中恢复原始的float值。在您提到的问题中,我只看到它提到了从double转换为float。 - ravin.wang
1
original_value 的类型是什么? - Caduchon
你是在问C还是C++? - Mohit Jain
这个问题,C和C++有什么区别吗? - ravin.wang
显示剩余3条评论
1个回答

阿里云服务器只需要99元/年,新老用户同享,点击查看详情
20
“fv”是否应该与“original_value”完全相等?任何精度可能会丢失吗? 是的,如果在两者之间未更改“dv”的值。 来自C99规范中的“Conversion 6.3.1.5 Real Floating types”部分: 1.当将float提升为double或long double,或将double提升为long double时,“其值不变”。 2.当将double降级为float,long double降级为double或float,或将以比其语义类型(见6.3.1.8)所需的更高精度和范围表示的值明确转换为其语义类型时,“如果可以在新类型中准确表示要转换的值,则保持不变。如果要转换的值位于可表示但无法准确表示的值范围内,则结果是实现定义方式选择的最接近的更高或更低的可表示值。如果要转换的值超出了可表示的值范围,则行为是未定义的。”

对于C++,来自第4.6节,也称为conv.fpprom(使用的草案:n337,我相信类似的规定在最终规范中也是可用的)

float类型的prvalue可以转换为double类型的prvalue。值不变。此转换称为浮点数提升。

以及第4.8节,也称为conv.double

浮点类型的prvalue可以转换为另一种浮点类型的prvalue。如果源值可以在目标类型中精确表示,则转换的结果是该精确表示。如果源值介于两个相邻的目标值之间,则转换的结果是这些值中任意一个的实现定义选择。否则,行为未定义。从允许作为浮点提升的转换中排除了浮点转换集合

因此,这些值应该完全相等。


需要注意的是,如果 OP 在片段中添加的 ... 行更改了 dv 的值,则可能会导致精度损失甚至 UB。 - Elias Van Ootegem
最初的问题“SHOULD fv与original_value完全相等吗?可能会丢失任何精度吗?”是两个问题,而答案“Yes”仅适用于第一个问题 - 看起来您希望对第二个问题回答“否”。建议进行小的编辑以澄清。 - chux - Reinstate Monica

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,