我正在读取 Fortran 中的一个文件,该文件每行都有不确定数量的浮点值(目前,一行上大约有 17 个值)。我想将每行的第 n 个值读取到给定的浮点变量。我该怎么做呢?
在 C 中,我编写的方式是将整行读入字符串,然后执行如下操作:
for(int il = 0; il < l; il++)
{
for(int im = -il; im <= il; im++)
pch = strtok(NULL, "\t ");
}
for(int im = -l; im <= m; im++)
pch = strtok(NULL, "\t ");
dval = atof(pch);
在这里,我不断地读取一个值并将其丢弃(从而缩短字符串),直到我准备好接受我正在尝试读取的值。
有什么办法可以在 Fortran 中做到这一点吗?在 Fortran 中是否有更好的方法来做到这一点?我的 Fortran 代码的问题似乎是
read(tline, '(f10.15)') tline1
不会缩短 tline (tline 是我的字符串,包含整行,tline1 是我试图将其解析成的内容),因此我无法使用与我在我的代码中相同的方法C 例程。
有什么帮助吗?
问题是 Fortran 是基于记录的 I/O 系统,而 C 是基于流的。
如果您可以访问 Fortran 2003 兼容编译器(现代版本的 gfortran 应该可以工作),您可以使用
stream
ACCESS
说明符来执行您想要的操作。
可以在此处找到示例。
当然,如果您真的愿意,您可以直接从 Fortran 使用 C 函数。两种语言的接口通常很简单,通常只需要一个带有小写名称和附加下划线的包装器(当然取决于编译器和平台)。来回传递数组或字符串通常并不是那么简单;但对于这个例子来说,这是不需要的。
一旦数据位于字符数组中,您就可以将其读入另一个变量,就像使用
ADVANCE=no
签名一样,即。
do i = 1, numberIWant
read(tline, '(F10.15)', ADVANCE="no") tline1
end do
其中
tline
应在循环末尾包含您的号码。
由于基于记录的 I/O,
READ
语句通常会抛出记录末尾之后的内容。但 ADVANCE=no
告诉它不要这样做。
如果您确切知道所需值从哪个位置开始,则可以使用
T
编辑描述符从该位置开始下一次读取。read(file_unit, '(t41, f10.5)') value1
P.s.:您可以在运行时动态创建格式字符串,并在
t
之后使用正确的数字,通过使用字符变量作为格式,并使用内部文件写入来放入该数字。n
开始的值。然后它看起来像这样(我在单引号和双引号之间交替,以尝试使每个字符串的开始和停止位置更清楚):
write(my_format, '(a, i0, a)') "(t", n, ', f10.5)'
read(file_unit, my_format) value1
或者,可以通过
WRITE
语句直接生成字符串作为输出,以去除任何不受欢迎的字符:
character(len=12), dimension( 12) :: file_name ! filename
character(len=24), dimension( 12) :: files ! directory path + filename
character(len= 8), dimension( 14) :: short ! stores filename without path & file extension
...
do i=1,m
files(i)= './debug/emi/'//file_name(i)
write(short(i),"(a8)") file_name(i)
end do
call show(io_unit, files, short)
!.. Generates the output
file #: 1 ./debug/emi/cicle_a2.dat cicle_a2
file #: 2 ./debug/emi/cicle_a5.dat cicle_a5