基本三角方程的浮点异常

时间:2017-02-09 04:39:58

标签: floating-point fortran gdb sigfpe

我在从地理坐标到地心坐标转换的子程序中遇到浮点异常问题。变量geo(x)作为纬度和经度对馈入子程序。变量xyz(x)输出为组件的三元组(x - 格林威治子午线和赤道; y - 90度经度和赤道; z - 北极)

subroutine geo2xyz(geo,xyz)
IMPLICIT REAL*8  (A-H,O-Z)
dimension geo(2),xyz(3)
rr=6367443.5
xyz(1)=rr*sind(90.-geo(1))*cosd(geo(2))
xyz(2)=rr*sind(90.-geo(1))*sind(geo(2))
xyz(3)=rr*cosd(90.-geo(1))
return
end

我意识到sindcosd是非标准函数,但它们通过适当的转换链接到目标文件。我之前测试过它,它适用于其他使用度而不是弧度的代码:

real function sind(x)
IMPLICIT REAL*8 (A-H,O-Z)
sind=sin(x*3.141592653589793d0/180.0d0)
return
end

real function cosd(x)
IMPLICIT REAL*8 (A-H,O-Z)
cosd=cos(x*3.141592653589793d0/180.0d0)
return
end

我尝试使用GDB进行程序,但无法弄清楚问题。似乎等式中的所有变量都可以,但xyz(1) = 1,如果我用计算器进行计算则不是这种情况。

Program received signal SIGFPE, Arithmetic exception.
0x0000000100001cb8 in geo2xyz (geo=..., xyz=...) at disslip.f:758
758     xyz(1)=rr*sind(90.-geo(1))*cosd(geo(2))
(gdb) print xyz(1)
$1 = 1
(gdb) print rr
$2 = 6367443.5
(gdb) print geo(1)
$3 = 50.350000000000001
(gdb) print geo(2)
$4 = -127.55800000000001
(gdb)

我在这里缺少什么导致浮点异常?我相信这很简单,我对此很新。

1 个答案:

答案 0 :(得分:4)

sind和cosd函数确实返回REAL(单精度)浮点。

subroutine geo2xyz对此没有任何线索 使用IMPLICIT REAL*8,它将假定这些函数返回双精度浮点。

因此,在使用它们之前,必须正确地声明sind和cosd为真,并且/或者将它们的返回类型更改为real * 8.

有趣的是,这个程序可能适用于旧的x86架构,因为返回的单个精度值在ST0寄存器中被提升为double。它不适用于使用SSE2并注册XMM0的64位intel:在这种架构中没有升级加倍。