gpt4 book ai didi

c++ - 浮点运算是否会导致 IEC 559/IEEE 754 浮点类型的无限未定义行为

转载 作者:可可西里 更新时间:2023-11-01 16:20:12 36 4
gpt4 key购买 nike

我正在通读 Infinity not constexpr ,这似乎表明创建无穷大是未定义的行为:

[expr]/4 :

If during the evaluation of an expression, the result is not mathematically defined or not in the range of representable values for its type, the behavior is undefined.

但是,如果std::numeric_limits::is_iec559 equals true,似乎给了我们更多的保证。

下面的代码利用这个保证来创建一个无限的数字。在 constexpr 上下文中执行时,它会导致编译器失败,因为如果 is_iec559 等于 false,这是未定义的行为

// clang++ -std=c++17 -O3
#include <limits>

constexpr double createInfinity()
{
static_assert(std::numeric_limits<double>::is_iec559, "asdf");
double d = 999999999999;
while (d != std::numeric_limits<double>::infinity())
{
d *= d;
}
return -1*d;
}

static_assert(createInfinity() == std::numeric_limits<double>::infinity(), "inf");

Code at Compiler Explorer

由于此函数总是产生无穷大,因此永远不能在有效的 C++ 程序中调用它。然而,正如我们在 is_iec559 上断言的那样,我们得到了额外的保证。这个程序还无效吗?

  • 如果无效? is_iec559 有什么意义?
  • 如果有效?为什么它在运行时有效而不是在 constexpr 上下文中?

(答案可以同时使用C++17和即将到来的C++20,请注明使用的是哪个)

最佳答案

等待一些时间有时会有所帮助,看起来 Clang 已经收到了一个可以编译此代码的补丁:https://reviews.llvm.org/D63793

Prior to r329065, we used [-max, max] as the range of representable values because LLVM's fptrunc did not guarantee defined behavior when truncating from a larger floating-point type to a smaller one. Now that has been fixed, we can make clang follow normal IEEE 754 semantics in this regard and take the larger range [-inf, +inf] as the range of representable values.

需要注意的有趣元素(该修订版中的部分代码注释)是导致 NaN 的操作(尚)不被允许:

// [expr.pre]p4:
// If during the evaluation of an expression, the result is not
// mathematically defined [...], the behavior is undefined.
// FIXME: C++ rules require us to not conform to IEEE 754 here.

Example at compiler explorer:

#include <limits>

constexpr double createNan()
{
static_assert(std::numeric_limits<double>::is_iec559, "asdf");
double d = std::numeric_limits<double>::infinity() / std::numeric_limits<double>::infinity();
return -1*d;
}

static_assert(createNan() != 0., "NaN");

关于c++ - 浮点运算是否会导致 IEC 559/IEEE 754 浮点类型的无限未定义行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56097944/

36 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com