【发布时间】:2015-12-24 23:39:56
【问题描述】:
如何检查 float 是否可以表示为整数类型,而无需通过强制转换来调用未定义的行为? §4.9.1 禁止这样做:
浮点类型的纯右值可以转换为 整数类型。转换截断;也就是小数部分 被丢弃。如果截断的值不能,则行为未定义 以目标类型表示,
对于 C 有 this 问题,但接受的答案显然会导致未定义的行为(首先是简单的强制转换,然后是使用 union hack,这让整个事情对我来说非常有问题)。
我明白很难有一个完全合规的解决方案,但是一个由实现定义的解决方案(假设 IEEE-754 浮动)也是可以接受的。
【问题讨论】:
-
检查原始值是否小于
numeric_limits<desinationType>::max()(明显扩展到负值)还不够吗?一旦它在范围内,那么截断的值应该是可表示的。 -
@Igor 但是比较如何进行呢?据我所知,这将再次涉及一些隐式转换,这会导致错误结果或 UB。,
-
比较将从整数转换为浮点数。这在典型实现上应该不是问题——即使 2^64 也在 32 位 IEEE
float的范围内。为了更加安全,在比较之前将两个值都转换为double。您需要 1000 位整数类型才能接近 64 位 IEEEdouble的限制。 -
我之前回答过但删除了答案,因为引用的问题似乎有一个很好且符合要求的答案stackoverflow.com/a/17822304/34509
-
@JohannesSchaub-litb:很好的发现,但最好有一个合适的 C++ 版本(通用,不假设特定类型)。因此,我认为不要将其作为重复项关闭。为翻译人员 +1。