Intel® Fortran Compiler
Build applications that can scale for the future with optimized code designed for Intel® Xeon® and compatible processors.
29251 Discussions

FORTRAN equivalent to a C fwrite?

david_sallngc_com
1,026 Views
Hi Everyone!

I am trying to read/write binary data to files in FORTRAN using the Intel compiler that will be read/write with Matlab. I have successfully done this however the runtime for large files is slow. A small example of my code for writting a binary file is,

real*8 a(10)
open(unit = 1, file = 'foo.dat', form = 'unformatted', recordtype = 'stream')
do i = 1,10
write(1) a(10)
end do

I believe that I am being slowed down by constantly fetching the A data in memory? Is there a way I can write the vector A as is done in C using FWRITE where one specifies the number of bytes and the loop is eliminated?

I also need to write COMPLEX data into the output. I am currently doing the following (Matlab stores real() and imag() data in separate vectors),

complex*16 b(10)

do i = 1,10
write(1) real(b(i))
end do
do i = 1,20
write(1) imag(b(i))
end do

Is there a way this can be done using a type of STRIDE variable as opposed to storing the real and imaginary parts in separate vectors? Since in FORTRAN, the real/imaginary parts are interlaced, is there a way of writing every other value? For example, if we were to write out B,

real(b(1)) imag(b(1)) real(b(2)) imag(b(2)) ...

byte chunk 1 byte chunk 2 byte chunk 3 byte chunk 4 .....

I would want to write byte chunk 1,3,5, ... for the reals and chunk 2,4,6,... for the imaginary data.

Thank you very much for your time. Any help would be greatly appreciated.

Sincerely,

David
0 Kudos
6 Replies
jimdempseyatthecove
Honored Contributor III
1,026 Views

write(1) A(1:10)
0 Kudos
Paul_Curtis
Valued Contributor I
1,026 Views
...
real*8 a(10)
open(unit = 1, file = 'foo.dat', form = 'unformatted', recordtype = 'stream')
do i = 1,10
write(1) a(10)
end do

I believe that I am being slowed down by constantly fetching the A data in memory? Is there a way I can write the vector A as is done in C using FWRITE where one specifies the number of bytes and the loop is eliminated?


Instead of Fortran WRITE, use the Win32 API function WriteFile:

lret = WriteFile(handl, LOC(A), 10*SIZEOF(A(1)), NULL, os)

This does exactly what you want.
0 Kudos
david_sallngc_com
1,026 Views

write(1) A(1:10)
Hi Jim!

Thanks Jim. I can not believe that is all that is necessary!

How about if my vector is complex? Is there a way to write all REAL's and IMAG's separately usig some type of indexing?

Thanks again.

Sincerely,

David
0 Kudos
david_sallngc_com
1,026 Views
Quoting - Paul Curtis

Instead of Fortran WRITE, use the Win32 API function WriteFile:

lret = WriteFile(handl, LOC(A), 10*SIZEOF(A(1)), NULL, os)

This does exactly what you want.
Hi Paul!

Thanks for the reply. I need code that will run on both Windows 32-bit and 64-bit as well as a 64-bit Linux. Even though WriteFile looks just like fwrite, I need something more portable.

Thanks again.

Sincerely,

David
0 Kudos
Les_Neilson
Valued Contributor II
1,026 Views
How about if my vector is complex? Is there a way to write all REAL's and IMAG's separately usig some type of indexing?


David,
write(1) (real(a(i)),i=1,10), (aimag(a(j)),j=1,10)

should work
Les
0 Kudos
Steven_L_Intel1
Employee
1,026 Views
You can open the file ACCESS='STREAM' and just write a stream of bytes. This is standard F2003.
0 Kudos
Reply