在fortran 90中打开并读取一行数据 [英] Open and read data in one row in fortran 90

查看:162
本文介绍了在fortran 90中打开并读取一行数据的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我做了一些虚拟代码来学习打开和读取文件。假设我有以下test.dat:

  1 
2
3
4
5
6
7
8
9
10

我写了下面的代码来打开和读取数据文件:

 子程序readdata 
implicit none

integer :: j
double precision :: test

open(unit = 100,file ='test.dat',status ='测试$ b $ print *,'N1 =',测试
结束$ $读取(100,*)测试
print *,'N1 =', b
$ b结束子程序

如预期的那样,输出如下所示

  gfortran -g -I / usr / include -o main main.o subroutines.o -L / usr / lib64 / liblapack -L / usr / lib64 / libblas 
test = 1.0000000000000000
test = 2.0000000000000000
test = 3.0000000000000000
test = 4.0000000000000000
test = 5.0000000000000000
test = 6.00000000000000 00
test = 7.0000000000000000
test = 8.0000000000000000
test = 9.0000000000000000
test = 10.000000000000000
主要完成。

但是,如果数据存储在单行中,如下所示:

  1 2 3 4 5 6 7 8 9 10 

那么上面的代码不能按需要工作。它只读取行中的第一个元素,然后提示一个错误。

  sharwani @ linux-h6qd:〜/ PHD_research / myCodes /数据> ./runcase.sh 
rm -f * .o * .mod * .MOD * .exe * .stackdump main
gfortran -g -I / usr / include -c main.f90
gfortran -g -I / usr / include -c subroutines.f90
gfortran -g -I / usr / include -o main main.o subroutines.o -L / usr / lib64 / liblapack -L / usr / lib64 / libblas
test = 1.0000000000000000
在文件subroutines.f90的第9行(unit = 100,file ='test.dat')
Fortran运行时错误:文件结尾

所以,我的问题是我有一个数据文件,其中包含2879(1 x 2879)数字存储在一行中。如何打开并读取数据文件中的所有数据?

每个Fortran 读取默认情况下,语句读取值列表,然后前进到下一行的开头。将 read 想象成在输入文件中移动光标,所以你的陈述

  read(100,*)test 


可以满足您的期望。当它们全部位于文件的同一行时,第一条读取语句读取一个值(即 test ),然后前进到下一行的开头以读取下一个值,但没有下一行,你会看到我们显示的运行时错误。

有两个简单的解决方案。

您可以在一条语句中从一行读取多个值,例如,您可以声明

  real,dimension(10):: test 

然后

  read(100,*)test 

应该一次性将所有值存入数组中。



其次,您可以使用非前进输入,它告诉处理器在每个读取语句。类似下面的内容(检查你的情况的编辑描述符)

  read(100,'(f8.2)',advance ='no')测试

如果您选择后一种方法,请不要忘记,从一行中读取所有的值,你可以跳到下一行的开头,这样你可能需要执行一个语句,比如

  read(100,*)

它不会读取任何值,但会前进到下一行。


I did some dummy code to learn to open and read file. Let's say I have the following test.dat which reads

1
2
3
4
5
6
7
8
9
10

I wrote the following code to open and read the data file

subroutine readdata
implicit none

integer             :: j
double precision    :: test

open(unit = 100, file = 'test.dat', status = 'old', action = 'read')
 do j = 1,  10
 read(100,*) test
 print *, 'N1=', test
end do

end subroutine

The output is shown below, as expected

 gfortran -g  -I/usr/include -o main main.o subroutines.o -L/usr/lib64/liblapack -L/usr/lib64/libblas
 test=   1.0000000000000000     
 test=   2.0000000000000000     
 test=   3.0000000000000000     
 test=   4.0000000000000000     
 test=   5.0000000000000000     
 test=   6.0000000000000000     
 test=   7.0000000000000000     
 test=   8.0000000000000000     
 test=   9.0000000000000000     
 test=   10.000000000000000     
 Main finished.

However, if the data is stored in a single row as follows

1 2 3 4 5 6 7 8 9 10

then the above code does not work as desired. It only reads the first element in the row and then prompt an error

sharwani@linux-h6qd:~/PHD_research/myCodes/data> ./runcase.sh
rm -f *.o *.mod *.MOD *.exe *.stackdump main
gfortran -g  -I/usr/include -c main.f90
gfortran -g  -I/usr/include -c subroutines.f90
gfortran -g  -I/usr/include -o main main.o subroutines.o -L/usr/lib64/liblapack -L/usr/lib64/libblas
test=   1.0000000000000000    
At line 9 of file subroutines.f90 (unit = 100, file = 'test.dat')
Fortran runtime error: End of file

So, my question is that I have a data file which contains 2879 (1 x 2879) numbers stored in a single row. How am I going to open and read all those numbers in the data file?

解决方案

Each Fortran read statement, by default, reads a list of values and then advances to the beginning of the next line. Think of read as moving a cursor through the input file as it works. So your statement

read(100,*) test

does what you expect when the numbers in the input file are on separate lines. When they are all on the same line in the file the first read statement reads one value (i.e. test) then advances to the beginning of the next line to read the next value but there isn't a next line and you get the runtime error you have shown us.

There are 2 straightforward solutions.

One, you could read multiple values from a line in one statement, for example, you might declare

real, dimension(10) :: test

then

read(100,*) test

should get all the values into the array in one go.

Second, you could use non-advancing input, which tells the processor to not skip to the beginning of the next line after each read statement. Something like the following (check the edit descriptor for your circumstances)

read(100,'(f8.2)',advance='no') test

If you choose this latter approach, don't forget that after you have read all the values from a line you do want to skip to the beginning of the next line so you may need to execute a statement such as

read(100,*)

which doesn't read any values but does advance to the next line.

这篇关于在fortran 90中打开并读取一行数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆