问题
I'm looking for a bulletproof way of converting logical type variables to real type that will work in both ifort and gfortran. The following works in ifort, but not in gfortran:
logical :: a
real :: b
a = .true.
b = dble(a)
The error thrown in gfortran is
b = dble(a)
1
Error: 'a' argument of 'dble' intrinsic at (1) must be a numeric type
Obviously, .true. should map to 1.d0, and .false. to 0.d0. What's the best way of doing this?
回答1:
I am not sure if there is an intrinsic tool that does this. I do not know why ifort accepts this, and my guess would be that it is a compiler specific functionality.
Edit: As pointed out in https://stackoverflow.com/a/15057846/1624033 below, there is the intrinsic merge function which is exactly what is needed here.
an option to to this, specifically since you want this to be bullet proof, is to create your own function.
I have not tested this, but the following might work:
elemental pure double precision function logic2dbl(a)
logical, intent(in) :: a
if (a) then
logic2dbl = 1.d0
else
logic2dbl = 0.d0
end if
end function logic2dbl
Edit: I added elemental to the function declaration based on advice below. I also added pure to this function as it adds the extra ability to use this in parallel situations and it is good documentation. This however is just my opinion and it is not necessary.
回答2:
In addition to writing a function to handle this, you could also directly use the intrinsic merge function: b = merge(1.d0, 0.d0, a)
. Or you could write a defined assignment subroutine that does this, so that you can just type b = a
.
回答3:
In gfortran, I am using the TRANSFER intrinsic for that type of job. Assuming a integer variable my_int then:
my_int = transfer(.false.,my_int)
the result of my_int is 0 as expected.
来源:https://stackoverflow.com/questions/15057429/convert-logical-type-to-double-in-fortran