【问题标题】:Confusing double precision real in Fortran在 Fortran 中混淆双精度实数
【发布时间】:2014-04-17 05:14:44
【问题描述】:

我现在有一个迫切的问题:在现代 Fortran 中声明双精度实数的“公认”方式是什么?按照从最旧到最新的顺序,故事似乎是这样的:DOUBLE PRECISION,然后是REAL(kind=8),然后是INTEGER, PARAMETER :: dp=kind(1.d0)REAL(kind=dp)--Metcalf 现在说dp=kind(0.d0)--现在是float32=selected_real_kind(6,37) 或@987654327 @。所以...

  1. 我现在应该如何声明双精度真实?
  2. kindREAL(kind=dp) 中是多余的吗?
  3. 在编译时是否需要任何特殊标志来使用gfortranifort 调用双精度实数?

【问题讨论】:

  • 我会问你所说的“双精度”是什么意思。该标准只是说精度必须大于默认实数的精度。如果您有一些特定要求,请使用 SELECTED_REAL_KIND。

标签: fortran


【解决方案1】:

我个人现在写

use, intrinsic :: iso_fortran_env

其中包含int32,real64等含义明显的参数,可以这样使用:

real(real64) :: a_64_bit_real_scalar

请注意,标准不保证kind=8 提供8 字节类型。 kind 参数采用的值不是标准化的,并且因编译器而异。

如果需要,您可以编写诸如

之类的语句
use, intrinsic :: iso_fortran_env, dp=>real64
...
real(dp) :: a_64_bit_real_scalar

【讨论】:

  • 这也是我的偏好。 real64iso_fortran_env 的 Fortran 2008 增强版。对我来说,这似乎普遍可用,例如,从 gfortran 4.5 开始。 iso_c_binding 类型的可用时间更长。
  • 请注意,real128 在 gfortran 中存在错误,它返回 10 字节实数而不是 16 字节实数。 (以防万一,您需要额外的高精度。)
  • gfortran 从 2011 年的 4.6 版开始支持真正的四精度。请参阅 gcc.gnu.org/ml/fortran/2011-07/msg00064.html
  • @kvantour,我的意思是使用 -fdefault-real-8 编译选项,而 USEing ISO_FORTRAN_ENV 在某些源文件中会在编译时引发 Warning: Use of the NUMERIC_STORAGE_SIZE named constant from intrinsic module ISO_FORTRAN_ENV at (1) is incompatible with option -fdefault-real-8。我发布了a question 并收到了答复。
  • @EnricoMariaDeAngelis,啊哈提出这个问题的好方法。 +1
【解决方案2】:

1)我现在应该如何声明双精度实数?

我个人更喜欢使用

integer, parameter :: wp = selected_real_kind(15,307)
real(wp) :: var

方法。但正如马克指出的那样,iso_fortran_env 是另一种直接的方法。如果您打算使用 C 接口,您可能想尝试ISO_C_BINDING 模块并使用

use iso_c_binding
real(c_double) :: var

得到你想要的双精度。

2) kindREAL(kind=dp) 中是多余的吗?

是的。

3) 在编译时是否需要任何特殊标志来使用gfortranifort 调用双精度实数?

对于gfortran,您可以使用编译标志-fdefault-real-8。对于ifort,您可以使用-real-size=64 标志。

【讨论】:

  • +1 以确保完整性,但请注意 -fdefault-real-8,因为它将 double precision 提升到 16 个字节,请咨询 man gfortran 并查看 -fdefault-double-8
【解决方案3】:

目前推荐的在 Fortran 中声明双精度实数的方法是:

INTEGER, PARAMETER :: rk = SELECTED_REAL_KIND(15, 307)
REAL(rk) :: x
...

【讨论】:

    猜你喜欢
    • 2016-11-08
    • 2010-12-04
    • 2017-01-06
    • 1970-01-01
    • 1970-01-01
    • 2014-05-29
    • 1970-01-01
    • 2019-09-28
    • 1970-01-01
    相关资源
    最近更新 更多