Difference between revisions of "Fortran issues"

From CUC3
Jump to navigation Jump to search
import>Jss43
 
import>Jss43
Line 34: Line 34:
 
1.234560
 
1.234560
 
1.23456000000000
 
1.23456000000000
  +
</pre>
  +
  +
But the -r8 flag can help. It's safer to specify the kind in the code though.
  +
  +
<pre>
  +
jss43@keiko:~/src/test> more testkind.f90 && ifort -r8 testkind.f90 && ./a.out program testkind
  +
implicit none
  +
integer,parameter :: r1=kind(0.0)
  +
integer,parameter :: r2=kind(0.d0)
  +
write (6,'(/a/)') 'Output:'
  +
write (6,*) real(1)
  +
write (6,*) real(1,r1)
  +
write (6,*) real(1,r2)
  +
write (6,*) real(1.23456d0)
  +
write (6,*) real(1.23456d0,r1)
  +
write (6,*) real(1.23456d0,r2)
  +
write (6,*) real(dcmplx(1.23456d0,0.2155660d0))
  +
write (6,*) real(dcmplx(1.23456d0,0.2155660d0),r1)
  +
write (6,*) real(dcmplx(1.23456d0,0.2155660d0),r2)
  +
end program testkind
  +
  +
Output:
  +
  +
1.00000000000000
  +
1.00000000000000
  +
1.00000000000000
  +
1.23456000000000
  +
1.23456000000000
  +
1.23456000000000
  +
1.23456000000000
  +
1.23456000000000
  +
1.23456000000000
 
</pre>
 
</pre>

Revision as of 15:54, 25 June 2008

I thought it would be useful to have a page for noting Fortran problems which aren't well documented elsewhere or are common gotchas... --james 16:23, 25 June 2008 (BST)

Real intrinsic

Care needs to be taken with using REAL(X). The default behaviour for REAL differs if X is complex rather than integer or real. Some googling reveals this is an oddity, but it is the specification. I have found that DREAL isn't always portable (some compilers have issues when the argument to DREAL is the value of a derived type, e.g. DREAL(X%v) fails at compile time but REAL(X%v) doesn't).

keiko:~/src/test> more testkind.f90 && ifort testkind.f90 && ./a.out 
program testkind
    implicit none
    integer,parameter :: r1=kind(0.0)
    integer,parameter :: r2=kind(0.d0)
    write (6,'(/a/)') 'Output:'
    write (6,*) real(1)
    write (6,*) real(1,r1)
    write (6,*) real(1,r2)      
    write (6,*) real(1.23456d0)
    write (6,*) real(1.23456d0,r1)
    write (6,*) real(1.23456d0,r2)      
    write (6,*) real(dcmplx(1.23456d0,0.2155660d0))
    write (6,*) real(dcmplx(1.23456d0,0.2155660d0),r1)
    write (6,*) real(dcmplx(1.23456d0,0.2155660d0),r2)      
end program testkind

Output:

   1.000000    
   1.000000    
   1.00000000000000     
   1.234560    
   1.234560    
   1.23456000000000     
   1.23456000000000     
   1.234560    
   1.23456000000000

But the -r8 flag can help. It's safer to specify the kind in the code though.

jss43@keiko:~/src/test> more testkind.f90 && ifort -r8 testkind.f90 && ./a.out program testkind
    implicit none
    integer,parameter :: r1=kind(0.0)
    integer,parameter :: r2=kind(0.d0)
    write (6,'(/a/)') 'Output:'
    write (6,*) real(1)
    write (6,*) real(1,r1)
    write (6,*) real(1,r2)      
    write (6,*) real(1.23456d0)
    write (6,*) real(1.23456d0,r1)
    write (6,*) real(1.23456d0,r2)      
    write (6,*) real(dcmplx(1.23456d0,0.2155660d0))
    write (6,*) real(dcmplx(1.23456d0,0.2155660d0),r1)
    write (6,*) real(dcmplx(1.23456d0,0.2155660d0),r2)      
end program testkind

Output:

   1.00000000000000     
   1.00000000000000     
   1.00000000000000     
   1.23456000000000     
   1.23456000000000     
   1.23456000000000     
   1.23456000000000     
   1.23456000000000     
   1.23456000000000