You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Fortran中重复读取文件同一行的报错问题及修复咨询

解决Fortran重复读取同一行数据时的"End of Record"报错问题

你的问题出在对advance='no'的理解和使用上:当你用read(ut, '(a)', advance='no')读取时,第一次就把文件里那一行的所有字符都读进了lnumber,此时文件指针已经停在该行的末尾。后续循环再执行读取操作时,当前记录(也就是这一行)已经没有剩余字符可以读取,所以触发了"End of record"的运行时错误。

下面给你几种针对性的修复方案,根据你的实际需求选择:

方案1:缓存行内容(推荐,效率更高)

先把整行内容一次性读取到变量中缓存起来,之后直接循环使用这个变量即可,不需要反复操作文件:

program advance
    implicit none
    integer , parameter :: ut = 20
    character(len=7) :: fname = 'dat.dat'
    integer :: n, idx
    character(len=100) :: lnumber

    open(unit = ut, file =fname, status='old', action='read')
    ! 一次性读取整行到缓存变量
    read(ut, '(a)') lnumber
    close(ut) ! 读完文件就可以关闭,避免资源占用

    n = 10
    do idx = 1, n
        print *, lnumber
    end do
end program advance

方案2:每次循环重置文件指针

如果你需要保持文件打开状态,可以在每次读取前用rewind命令把文件指针重置到文件开头(因为你的文件只有一行,重置开头就相当于回到该行起始位置):

program advance
    implicit none
    integer , parameter :: ut = 20
    character(len=7) :: fname = 'dat.dat'
    integer :: n, idx
    character(len=100) :: lnumber

    open(unit = ut, file =fname, status='old', action='read')

    n = 10
    do idx = 1, n
        rewind(ut) ! 重置指针到文件开头
        read(ut, '(a)') lnumber
        print *, lnumber
    end do
    close(ut)
end program advance

方案3:直接读取数值(如果你的目标是处理实数值)

既然你的文件里是实数值,没必要读取字符串,直接读取到数值变量里再循环使用会更简洁:

program advance
    implicit none
    integer , parameter :: ut = 20
    character(len=7) :: fname = 'dat.dat'
    integer :: n, idx
    real(kind=8) :: val ! 用双精度类型存储长精度的实数值

    open(unit = ut, file =fname, status='old', action='read')
    read(ut, *) val ! 直接读取数值
    close(ut)

    n = 10
    do idx = 1, n
        print *, val
    end do
end program advance

总结一下:advance='no'的作用是读取后不切换到下一个记录,但它不会自动重置当前记录的指针,也不会重复读取已经读完的内容。所以要么提前缓存内容,要么手动重置指针,才是正确的重复读取方式。

内容的提问来源于stack exchange,提问作者Many

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.27 09:39:06