operator overloading - Fortran: Accessing values from the return type of a function -
i have created derived type v, , included add function can use operator +.
however when
z = u + v   the operation not performed. think because z%kn  not being accessed.
however when
call vsum(z, u, v)    everything works expected
below declaration of derived type , overloading function vadd.
module vtest  type :: v    character (len=8) :: kn   real,  allocatable :: vc(:)    contains      procedure :: vadd     generic :: operator (+) => vadd   end type vtest  contains  function vadd (b, c) result (a)   type (v) ::   class (v), intent (in) :: b, c    !!$ in vsum, use made of a% kn    call vsum (a, b, c)  end function vadd   subroutine vsum (ta, tb, tc)    type (v), intent (inout)  :: ta    type (v), intent (in) :: tb, tc     logical :: la, lb, lc     la = .false.;  lb = .false.;  lc = .false.     select case (ta%kn)      case ("real32")      if (allocated (ta%vc)) la = .true.      if (allocated (tb%vc)) lb = .true.      if (allocated (tc%vc)) lc = .true.      if (la .and. lb .and. lc)         ta%vc = tb%vc + tc%vc      end if     end select   end subroutine vsum  end module vtest   program test use vtest type (v) :: z     z% kn = "real32"    allocate (z% vc_real32(3))    write (*,*) "z = u + v"    write (*,*) "z% kn: ", z% kn    z = u + v    write (*,*) "z% kn: ", z% kn    write (*,*) "z: ", z% vc_real32  end program vtest      
let's @ subroutine vsum.  work done in subroutine depends on definition of components of 3 objects ta, tb , tc.  summation proceed expect necessary allocatable components allocated , match of ta%kn 'real32'.
there's no complete working example, things work when there call like
call vsum(z, u, w)  ! v name of type, call variable w   z%kn set 'real32'.
however, defined operation
z = u + w   there function reference
z = vadd(u, w)   in there call
call vsum (a, b, c)  ! actual arguments "z", u, w.   now, a function result of vadd.  consequent of that, dummy argument intent(out) a undefined.
that means, essentially, when passed through vadd z makes vsum undefined component kn , unallocated component vc.  so, requirements summation not met (and indeed select case forms invalid reference).
i suppose can comment on how fix issue, also.
in vsum, you're taking, in effect, type of operation "result".  instead, like
subroutine vsum (ta, tb, tc)   type (v), intent (out)  :: ta   type (v), intent (in) :: tb, tc    logical :: lb, lc    lb = .false.;  lc = .false.    ! in here want consistency checking...   select case (tb%kn)       case ("real32")     if (allocated (tb%vc)) lb = .true.     if (allocated (tc%vc)) lc = .true.     if (lb .and. lc)        ta%vc = tb%vc + tc%vc   ! ta%vc being automatically allocated     end if   end select   end subroutine vsum   this, naturally, doesn't address seeming desire (from title) take type of operation result. could original subroutine approach, except in 1 instance isn't philosophy of fortran functions.
if want use defined operations, can't have operation defined left-hand side of assignment.  in expression u+w there isn't left-hand side, defined operation still expected behave.  say, in statement
z = u + w   you aren't saying "z result of operation + applied u , w".  but: "the operation + applied u , w evaluated , result (through defined or implicit assignment) assigned z".  there assignment before "type of result" reached.  why earlier on put z actual argument in quotes.
Comments
Post a Comment