A more efficient way to directly use member variables of a derived type without using the percentage sign

170 Views Asked by At

As shown in using fortran derived type variable without %, we can use associate to avoid using the percentage sign. An example is as below:

    program test
    type z_type
    real x,y
    end type z_type
    type(z_type) :: z
    associate (x=>z%x)
    associate (y=>z%y)
    x=10
    y=10
    write(6,*)z%x,z%y
    end associate
    end associate
    end

But if I have too many member variables in the derived type, are there any "efficient " way for me to get what the above "associate " approach does?
Thanks. An update: the problem is that I am refactoring a legacy code, in which I need to wrap up many variables to a derived type structure. But I hope I don't need to add to each variable in the block of the previous codes with the derived data name followed by % sign.

1

There are 1 best solutions below

1
lastchance On BEST ANSWER

Well, you could use pointers, I suppose, but it's a bit unnatural.

program test
   implicit none

   type z_type
      real x, y
   end type z_type

   type(z_type), target :: z
   real, pointer :: x, y

   x => z%x
   y => z%y

   x = 10
   y = 20

   write( *, * ) z

end program test

If the variables were all of one type then Fortran arrays are devastatingly effective:

program test
   implicit none

   type z_type
      real x(2)
   end type z_type

   type(z_type) z
   z%x = [ 10, 20 ]

   write( *, * ) z

end program test

Overall, it might be better to make z_type a proper class, with its own type-bound procedures (aka member functions) and just make it object-oriented programming.

module modz
   implicit none

   type z_type
      real x, y
   contains
      procedure write_me
   end type z_type

contains

   subroutine write_me( this )
      class(z_type), intent(in) :: this
      write( *, *) this%x, this%y
   end subroutine write_me

end module modz

!=======================================

program test
   use modz
   implicit none

   type(z_type) :: z = z_type( 10, 20 )
   call z%write_me

end program test