How can I read and write 3D arrays in Fortran?

  • Context: Fortran 
  • Thread starter Thread starter rose2718
  • Start date Start date
  • Tags Tags
    3d Arrays Fortran
Click For Summary

Discussion Overview

The discussion centers around reading and writing 3D arrays in Fortran, specifically focusing on the I/O operations for a 3D array u(n,m,2) where n and m represent dimensions in a grid. Participants explore various methods for outputting the array to a text file and subsequently reading it back into another array, addressing both formatted and binary approaches.

Discussion Character

  • Technical explanation
  • Debate/contested
  • Mathematical reasoning

Main Points Raised

  • One participant shares a method for writing a 3D array to a file in a format suitable for gnuplot, asking for advice on reading it back.
  • Another participant suggests writing the data in binary format to save disk space, while noting potential issues with human readability and portability.
  • A different approach is proposed to include x and y coordinates with the data to ensure integrity and facilitate reading back the data correctly.
  • One participant encounters a runtime error when attempting to read data back, leading to a modified reading method that omits the coordinate checking.
  • Another participant mentions that the writing can be done without loops, but a similar error occurs when reading back the data, prompting questions about the cause of the error.
  • It is noted that skipping lines in the output file could lead to issues when reading back the data, emphasizing the importance of maintaining consistency in the read and write formats.
  • Participants discuss the necessity of checking the last values of the array after reading to ensure data integrity.

Areas of Agreement / Disagreement

Participants express differing opinions on the best methods for writing and reading the array data, with some advocating for including coordinates and others suggesting simpler methods. There is no consensus on a single best approach, and some issues remain unresolved, particularly regarding error handling during the read process.

Contextual Notes

Participants mention potential limitations related to skipping lines in the output file and the need for careful handling of array sizes when reading back data. There are also unresolved questions about the runtime errors encountered during the reading process.

rose2718
Messages
4
Reaction score
0
Hi!

I have a 3D array u(n,m,2), where n=2000, m=200 are the xy-coordinates, and u(n,m,1) and u(n,m,2) store values of variables a and b computed at the coordinates.

(not very familiar with fortran I/O for arrays, when new lines are started, etc).

I'd like to output this array into a text file, and read it in at a later point in the program (fortran 95). The following output works fine, and is set up perfectly for gnuplot:

open(17,file='values.dat',action='write')
do x=1,n
do y=1,m

write(17,'(2(E10.4,1X))') u(x,y,1),u(x,y,2)

enddo

write(17,*) !skip a line

enddo
close(17)


This writes 2000 blocks of 200 x 2 arrays separated by a space, column 1 are 'a' values, column 2 'b' values.

How can I read this from values.dat into another 3D array later in the program, ie, v(n,m,2)? Is there a better way to write to the file (ie make two files, for a and b) that will make reading into v easier?

Thanks! =]
 
Technology news on Phys.org
It is possible to save some disk-space by writing the data in binary, such as a direct-access file, or using the binary format. The downside is that the file will not be easily human readable, and portability between systems could be an issue. However, you seem to write sequentially and read sequentially, once per run, so efficiency should not be a big issue.

> write(17,'(2(E10.4,1X))') u(x,y,1),u(x,y,2)

I personally would prefer a little redundancy and write x,y together with the data to ensure integrity. In addition, I would add a header to check for the size of the array before reading data, something like:

Code:
open(17,file='values.dat',action='write')
write(17,'(2I5)') n,m
do x=1,n
do y=1,m
write(17,'(2I5,2E12.4)')x,y,u(x,y,1),u(x,y,2)
enddo
*write(17,*) !skip a line  not required
enddo
close(17)

So when you read back the data, you can double-check the size of the array before reading, you would know when to end the reading (n*m lines) and the x, y coordinates would not be mixed up with rows and columns, or accidentally offset.

You can read it back using something like:

Code:
open(17,file='values.dat',action='read')
read(17,'(2I5)') n,m
C do some array size checking here
do =1,n*m
read(17,'(2I5,2E12.4)')x,y,u(x,y,1),u(x,y,2)
C or, if preferred
C read(17,'(2I5,2E12.4)')x,y,tmp,v(x,y,2)   skips the first value
enddo
close(17)
 
Thanks mathmate, your info was very helpful!

I got a runtime error at the line: read(17,'(2I5,2E12.4)')x,y,u(x,y,1),u(x,y,2)
error: Traceback: (Innermost first)

I ended up using:

do x=1,n
do y=1,m
read(19,'(2E12.4)')u(x,y,1),u(x,y,2)
enddo
enddo

which leaves out your useful array size-checking line, and keeping x,y with the data points, but works nonetheless.

Thanks again! :smile:
 
You actually don't even need the do loops. You can simply
Code:
open(11,file='filename.x',form='formatted')
write(11,*) u
!
!
read(11,*) u
As long as the array is the proper size when you're reading it in, it'll be fine.
 
Thanks minger. The writing works fine without do loops, but I get the "Traceback: (Innermost first)" error again when trying to read back in. Any idea why this error would show up?

Thanks!
 
Yes, you have the right statement to read the previous file that you wrote without the x,y values.
Basically, you use the same format to read and to write.
Be very careful, though, since you have skipped a line in your previous file after every 200 pairs of data, you would have to read it back in with the line skipping, or else they would show up as a pair if zeroes. This is where the x,y coordinate checking would avoid this problem. You must, however, write the file with the x,y u1, u2 before you can read it back with the x,y.
 
Okay, great! I left out the skipping a line part, as you mentioned it isn't needed.

Thanks again!
 
Do print the last values of u1 and u2 to make sure that nothing had been shifted as you read the values back into the program.
 

Similar threads

  • · Replies 20 ·
Replies
20
Views
3K
  • · Replies 4 ·
Replies
4
Views
3K
  • · Replies 8 ·
Replies
8
Views
2K
  • · Replies 8 ·
Replies
8
Views
2K
  • · Replies 13 ·
Replies
13
Views
3K
  • · Replies 8 ·
Replies
8
Views
2K
Replies
7
Views
3K
  • · Replies 6 ·
Replies
6
Views
2K
  • · Replies 1 ·
Replies
1
Views
4K
  • · Replies 19 ·
Replies
19
Views
7K