-->

Numerical Precision in Fortran 95:

2019-09-01 22:47发布

我有以下的Fortran代码:

Program Strange
   Real(Kind=8)::Pi1=3.1415926535897932384626433832795028841971693993751058209;
   Real(Kind=8)::Pi2=3.1415926535897932384626433832795028841971693993751058209_8;

   Print*, "Pi1=", Pi1;
   Print*, "Pi2=", Pi2;

End Program Strange

我编译gfortran,输出为:

 Pi1=   3.1415927410125732     
 Pi2=   3.1415926535897931

当然,第二个是正确的,但应该是这种情况? 这似乎是PI1被输入到存储器作为单精度数,然后放入一个双精度存储器插槽。 但是,这似乎是一个错误给我。 我对么?

Answer 1:

我知道一点的Fortran的! @杜格尔的答案是正确的,虽然他从引述片段不是,嵌入字母d变成一个真正的常量并不需要(因为Fortran 90中),确实有很多的Fortran程序员现在认为这种做法为过时。 该片段也被误导在咨询中使用的3.1415926535d+0初始化为圆周率64位浮点值,它不设置足够的位数到其正确的值。

该声明:

Real(Kind=8)::Pi1=3.1415926535897932384626433832795028841971693993751058209

定义Pi1来样8的实变量的字面真实值3.1415926535897932384626433832795028841971693993751058209然而是,默认类型的实际值,最有可能是在大多数当前的编译器4字节真实。 这似乎可以解释你的输出。请检查您的文档。

在另一方面,字面真实值Pi2=3.1415926535897932384626433832795028841971693993751058209_8是,由各种规格的后面添加,宣布为种类= 8,其是相同的种类被分配给变量的。

三个要点:

1)不陷入认为的陷阱kind=8表示相同的事情64-bit floating-point numberdouble 。 对于很多编译它,对于一些事实并非如此。 一种数字不是Fortran的实现之间移植。 他们是,根据标准,任意正整数。 好,拥有现代化的编译器,将是从内在模块使用预定义的常量iso_fortran_env ,如

use, intrinsic :: iso_fortran_env
...
real(real64) :: pi = 3.14159265358979323846264338_real64

还有其他的便携式方法来设定使用函数变量种如selected_real_kind

2)由于价值pi是不可能程序的执行过程中改变你可能不在乎,使其参数这样的:

real(real64), parameter :: pi = 3.14159265358979323846264338_real64

3)这是没有必要(或通常的),以结束与Fortran语句“;” 除非你想对源文件相同的线多条语句。



Answer 2:

我真的不知道Fortran语言,但这个页面说:

“D”字母必须嵌入文字,否则,编译器的预处理器将圆其关闭是一个单精度文字。 例如,3.1415926535将被读为3.141593而3.1415926535d + 0将被存储的所有完整的数字。 对于双精度数字字母“d”的含义为“E”为单精度的数字相同。

所以它看起来像你的猜测是正确的。



文章来源: Numerical Precision in Fortran 95: