优化Fortran ascii文件IO
我正在做一个项目,我需要将一些现有数据以ascii码的形式写入磁盘。我有一些工作,但IO本身是相当昂贵的,我想进一步优化它 数据基本上是一个实数数组,但是有些列存储编码的字符串,这些字符串需要重新编码为字符串(不要问!)。这个问题的输入和输出超出了我的控制范围,我正在接收这个真实数组,需要将它写成ascii码 我知道以无格式写入方式一次性写入数组会更快,但这并不能正确处理字符串列。有什么想法吗 下面是一些示例代码:优化Fortran ascii文件IO,fortran,Fortran,我正在做一个项目,我需要将一些现有数据以ascii码的形式写入磁盘。我有一些工作,但IO本身是相当昂贵的,我想进一步优化它 数据基本上是一个实数数组,但是有些列存储编码的字符串,这些字符串需要重新编码为字符串(不要问!)。这个问题的输入和输出超出了我的控制范围,我正在接收这个真实数组,需要将它写成ascii码 我知道以无格式写入方式一次性写入数组会更快,但这并不能正确处理字符串列。有什么想法吗 下面是一些示例代码: program test implicit none integer(kind
program test
implicit none
integer(kind=4), parameter :: nrows = 5000
integer(kind=4), parameter :: ncols = 400
integer, parameter :: real_kind = 8
integer(kind=4) :: i,j, handle
character(len=256) :: value_str
character(len=1) :: delimiter
real(kind=real_kind) :: data(nrows,ncols)
delimiter = " "
data(:,:) = 999.999
! Some examples of the "string columns"
data(:,10) = transfer(' foo ',data(1,1))
data(:,20) = transfer(' bar ',data(1,1))
handle=10
open(handle,file="out.txt",status="replace", access="stream")
do i=1,nrows
do j=1,ncols
! If this column contains encoded strings then recast
if((j==10).or.(j==20))then
write(handle) delimiter
value_str = transfer(data(i,j),value_str(1:real_kind))
write(handle) trim(value_str)
else
write(value_str,*) data(i,j)
write(handle) trim(value_str)
endif
enddo
write(handle) new_line('x')
enddo
close(handle)
end program test
gfortran test.F90-o test.x
时间测试
真0m2.65s
用户0m2.24s
系统0m0.04s
编辑:从原始test.F90代码示例中删除“if(j/=1)”以响应注释。使用自由格式,让系统为您处理更多内容。在这个命题中,我预先处理传输,并使用单个循环将数据写入文件。如果像示例中的2这样只有很少的字符数据列,那么这非常方便 您的代码将如下所示
program test
implicit none
integer(kind=4), parameter :: nrows = 5000
integer(kind=4), parameter :: ncols = 400
integer, parameter :: real_kind = 8
integer, parameter :: pos1 = 10 ! I like named constants
integer, parameter :: pos2 = 20 ! I like named constants
integer(kind=4) :: i,j, handle
character(len=256) :: value_str
character(len=1) :: delimiter
real(kind=real_kind) :: data(nrows,ncols)
character(real_kind), dimension(nrows,2) :: cdata ! two columns array for
delimiter = " "
data(:,:) = 999.999
! Some examples of the "string columns"
data(:,pos1) = transfer(' foo ',data(1,1))
data(:,pos2) = transfer(' bar ',data(1,1))
handle=10
open(handle,file="out.txt",status="replace", form="formatted")
! Transfer beforehand
cdata(:,1) = transfer( data(:,pos1), cdata(1,1) )
cdata(:,2) = transfer( data(:,pos2), cdata(1,1) )
do i=1,nrows
write(handle,*) data(i,1:pos1-1), cdata(i,1)&
, data(i,pos1+1:pos2-1), cdata(i,2)&
, data(i,pos2+1:)
enddo
close(handle)
end program test
给我这个时间
时间./test.x
实0m1.696s
用户0m1.661s
系统0m0.029s
而不是
时间./test.x
真正的0m2.654s
用户0m2.616s
系统0m0.032s
在我的计算机上什么是“但这不能正确处理字符串列”是什么意思?数据格式的示例在哪里?如果运行上面提供的test.F90代码并查看out.txt,则可以看到数据格式。您可以将字符串读取为“foo”和“bar”,即人类可读。