gpt4 book ai didi

c++ - 着色器中自己的 double cos() 实现的结果是 NaN,但在 CPU 上运行良好。出了什么问题?

转载 作者:可可西里 更新时间:2023-11-01 17:59:19 24 4
gpt4 key购买 nike

正如我所说,我想在带有 GLSL 的计算着色器中实现我自己的 double cos() 函数,因为浮点只有一个内置版本。

这是我的代码:

double faculty[41];//values are calculated at the beginning of main()

double myCOS(double x)
{
double sum,tempExp,sign;
sum = 1.0;
tempExp = 1.0;
sign = -1.0;

for(int i = 1; i <= 30; i++)
{
tempExp *= x;
if(i % 2 == 0){
sum = sum + (sign * (tempExp / faculty[i]));
sign *= -1.0;
}
}
return sum;
}

此代码的结果是,总和在着色器上为 NaN,但在 CPU 上算法运行良好。我也尝试调试这段代码,得到以下信息:

  • faculty[i] 对于所有条目都是正数且不为零
  • 每一步的tempExp都是正值
  • 在每个步骤中没有其他变量是 NaN
  • 第一次sum为NaN是在i=4的步

现在我的问题是:如果每个变量都是一个数字并且没有任何内容被零除,那么究竟会出现什么问题,特别是当算法在 CPU 上运行时?

最佳答案

让我猜猜:

首先您确定问题出在循环中,并且您仅使用以下操作:+*/

从这些操作中生成 NaN 的规则是:

  • 分区 0/0±∞/±∞
  • 乘法 0×±∞±∞×0
  • 加法 ∞ + (−∞)(−∞) + ∞ 和等价减法

通过声明 faculty[] 已正确初始化,您排除了 0/0±∞/±∞ 的可能性。

变量sign总是1.0-1.0所以它不能通过生成NaN >* 操作。

如果 tempExp 变为 ±∞,剩下的就是 + 运算。

所以可能 tempExp 在您的函数入口处过高并变为 ±∞,这将使 sum± ∞ 也是。在下一次迭代中,您将通过以下方式触发 NaN 生成操作:∞ + (−∞)。这是因为您将加法的一侧乘以 sign 并在每次迭代时在正负之间切换符号。

您正在尝试使 cos(x) 接近 0.0。因此,您应该使用 cos() 函数的属性将您的输入值减少到接近 0.0 的值。理想情况下在 [0, pi/4] 范围内。例如,删除 2*pi 的倍数,并在 [pi/4, pi/2] 中获取 cos() 的值在 0.0 附近计算 sin(x) 等等。

关于c++ - 着色器中自己的 double cos() 实现的结果是 NaN,但在 CPU 上运行良好。出了什么问题?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28877222/

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