1

我正在尝试使用 fortran 写出一个逗号分隔的文件以导入另一个商业包。问题是我有未知数量的数据列。我的输出需要如下所示:

a_string,a_float,a_different_float,float_array_elem1,float_array_elem2,...,float_array_elemn

这将导致可能如下所示:

L1080,546876.23,4325678.21,300.2,150.125,...,0.125
L1090,563245.1,2356345.21,27.1245,...,0.00983

我有三个问题。一、我希望元素被紧密分组(可变列宽),二、我不知道如何在格式语句中定义可变数量的数组元素,三、数组元素可以跨越很大的范围——可能是 12 个数量级。以下代码在概念上符合我的要求,但变量“n”和缺少列宽定义会引发错误(当然):

WRITE(50,900) linenames(ii),loc(ii,1:2),recon(ii,1:n)
900 FORMAT(A,',',F,',',F,n(',',F))

(我应该注意,n 在运行时是固定的。)当我执行 WRITE(50,*) 时,write 语句执行我想要的操作,除了它是宽度分隔的。

我认为这个线程几乎回答了我的问题,但我很困惑:所以。现在我有一个用 awk 解决问题的 shell 脚本,但那个解决方案是......不优雅。我可以进行一些操作以使输出成为字符串,然后直接编写它,但如果可能的话,我宁愿避免使用该选项。

我在 Fortran 90 中执行此操作,但我想尝试使我的代码尽可能向后兼容。

4

2 回答 2

2

接近您想要的格式是 f0.3,这将不提供空格和固定的小数位数。我认为,如果您还想删除尾随零,则需要做很多工作。

您的 write 语句中的“n”可能大于数据值的数量,因此一种(老派)方法是在那里放一个大数字,例如 100000。现代 fortran 确实有一些语法来指定无限重复,我是肯定有人会提供的。

----编辑无限重复就像你可能猜到的一个星号..并且在 f2008 中显然是“全新的”

于 2013-02-27T18:28:09.423 回答
1

为了确保行中的条目之间没有空格,您可以将它们分别写在字符变量中,然后使用adjustl()fortran 中的函数将它们打印出来:

program csv
  implicit none

  integer, parameter :: dp = kind(1.0d0)
  integer, parameter :: nn = 3
  real(dp), parameter :: floatarray(nn) = [ -1.0_dp, -2.0_dp, -3.0_dp ]
  integer :: ii
  character(30) :: buffer(nn+2), myformat

  ! Create format string with appropriate number of fields.
  write(myformat, "(A,I0,A)") "(A,", nn + 2, "(',',A))"
  ! You should execute the following lines in a loop for every line you want to output
  write(buffer(1), "(F20.2)") 1.0_dp  ! a_float
  write(buffer(2), "(F20.2)") 2.0_dp  ! a_different_float
  do ii = 1, nn
    write(buffer(2+ii), "(F20.3)") floatarray(ii)
  end do
  write(*, myformat) "a_string", (trim(adjustl(buffer(ii))), ii = 1, nn + 2)

end program csv

上面的演示仅适用于一个输出行,但您可以轻松地围绕适当的块编写一个循环来为所有输出行执行它。此外,如果您愿意,您可以为不同的条目选择不同的数字格式。

于 2013-02-27T19:41:54.203 回答