Reading file contain '' . '' issue

Deal all,
I have an extremely simple example, but I am confused if read can correctly recognize the '"." in the file.
Here is the file, call it test.csv

101,1,0,2,55,.,.,1

Note that the . cause trouble.

I was think read * can recognize . as just 0.0, but it seems behave strange. Here is the code,

program main
    implicit none
    integer :: fu, rc
    integer :: i(10)
    real :: x(10)   
    open(action='read', file='test.csv', iostat=rc, newunit=fu)
    read (fu, '(2(i10),6(g15.7))', iostat=rc) i(1:2),x(1:6)
    write(6,*) 'i = ', i(1:2)
    write(6,*) 'x = ', x(1:6)
    close(fu)
end program main

I expect it shows

i =  101    1
x =  0.0    2.0   55.0  0.0   0.0   1.0

but it gives me

  i =          101           1
 x =   0.0000000E+00  2.0000000E-07  5.5000000E-06  0.0000000E+00  0.0000000E+00
  1.0000000E-07

Obviously when encounter " . ", it cannot recognize anything after it.
Initially I use

read (fu, *, iostat=rc) i(1:2),x(1:6)

But the * does not help.

Could anyone explain why the ’ . ’ cause the trouble or how to make it work?

Do I have to read the whole line as string first, then deal with those , and . symbols and do some conversion? like things below,

Then the code becomes,

program main
    implicit none
    integer :: fu, rc
    integer :: i(10)
    real :: x(10)   
    character(len=100) :: char(8)
    open(action='read', file='test.csv', iostat=rc, newunit=fu)
    read (fu, *, iostat=rc) char(1:8)
    write(6,*) 'char = ', char(1:8)
    close(fu)
end program main

I can convert my char array correspondingly

Thank you very much in advance!

One technique to read CSV file (at least the version that contains commas or semicolons) is to use list-directed read - β€œread(fu,*) …”. List-directed read takes care of splitting the line into the right pieces, at least most of the time (spaces can get in the way). Safest to read it in as character strings and then read the right values from that.

Note that a single dot is not accepted as a number - hence reading from a character string will help.

The strange result you get is due to the formatted read: i10 means that 10 characters will be consumed and then the program attempts to convert the sequence of characters into an integer number. Depending on the details of that conversion the comma may be ignored as in your case. I would not have expected that though. Similar for the F format. This has an additional rule: if in the character representation of a real number a decimal is missing and you specify the number of decimals as larger than zero, a decimal will be inserted. I do not know the precise rules as I usually/always avoid that feature, but that explains the β€œe-7” part.

1 Like