pow(1, inf) == nan?
pow(1, inf) == nan?
我注意到我的一个计算着色器中有一些奇怪的行为,它们会意外地返回nan。仔细调查后,我发现pow
就是罪魁祸首:
pow(1, inf) == NaN
从C/c++的角度来看,我希望pow(1, inf) == 1
:
pow(+1, exponent)对于任何指数都返回1,即使指数是NaN
GLSL的pow
定义这个输入吗?
我只在规范中发现base < 0
和base == 0 && exponent <= 0
的常见异常。
@Damon的回答很接近,但是抄袭了spec中的一个错误:
pow(x, y) == exp2(x * log2 (y))
其中x和y交换了。应该是
pow(x, y) == exp2(y * log2 (x))
(测试例pow(2, 3)
)
使用正确的公式我们得到
pow(1, inf) == exp2(inf * log2(1)) == exp2(inf * 0) == exp2(nan) == nan
虽然计算着色器暗示您使用GPU和GLSL版本(> 1.30)来执行IEEE兼容的浮点数学,但不幸的是,这不是您可以理所当然的事情。所以…这里有龙。
您从c++的角度引用c++参考的推理是合理和正确的,但它省略了一个小而重要的句子:"如果实现支持IEEE浮点运算(IEC 60559),"。这句话强调了它既不是c++的要求(只是巧合,因为IEEE 754要求它,而通常 c++实现符合IEEE),也不是严格的保证(完全允许c++实现而不是实现IEEE 754)。
进一步,GLSL 不是 c++。对于算术来说,这可能会让人感到惊讶,因为尽管它显然不是同一种语言,但人们可以期望数学仍然是一样的,不是吗?
嗯,没有。pow(x, y)
在GLSL中被定义为exp2(x*log2(x))
(尽管在线手册页所基于的8.2没有明确地这样说)。它从前面提到的4.7.1中描述的表达式继承了精度。没有说明pow(1, x)
等于1
。
现在,用可能正确的中间结果展开上述表达式,正确的结果应该是+INF
,因为log2(+INF) = +INF
和1*+INF
仍然是+INF
和exp2(+INF) = +INF
。
但是,标准并没有真正定义这个。它只显式(un)定义零指数。
- g++的分段错误(在NaN上使用to_string两次时)
- 输出是NaN,如何
- 为什么我在输出端得到 nan?
- 提升反序列化对象具有 nan 或 -nan 值
- Is !NaN not a NaN?
- NaN 上的宇宙飞船操作员
- C++ STL 排序会检查 NaN 吗?
- C++ 每次运行程序时我都会"nan"输出的问题
- 复制 -nan 表示浮点数,AVX __m256 复制后显示 0
- 如何使用 Node-addon-API 实现 node-nan 回调
- 为什么我的双变量通过添加 c++ 显示 nan?
- nan() 函数的参数
- 如何检查 log2 'inbuilt c++ function'是否返回 '-inf'?
- 为什么 acos() 在使用点积的结果时会导致"nan(ind)"?
- 如何在 c++ 中处理 -nan 输出
- 为什么这段代码返回 -nan(ind)?C++
- 是否可以将"inf"分配给变量,例如 c++ 中的常规数值
- 在constexpr变量模板中模拟nan/inf
- C++ NAN、INF(非收敛)的 std::complex<> 数据类型测试
- pow(1, inf) == nan?