Fortran polymorphism in pointers

When you have polymorphism like this there are two things to consider about an object: its dynamic type and its declared type. The parameters component of test_mask (base_mask) is declared as

class(base_pars),pointer :: parameters

Such a component therefore has declared type base_pars.

Come the pointer assignment

mask_test%parameters=>par_test

mask_test%parameters has dynamic type the same as par_test: test_pars. It’s of declared type base_pars, though, and it’s the declared type that is important when we care about its components and bindings. base_pars indeed has no whoami.

You need, then, something which has declared type par_test. Without changing the definitions of the derived types you can do this with the select type construct.

select type (pars => mask_test%parameters)
class is (par_test)
  iostat=pars%whoami()  ! pars of declared type par_test associated with mask_test%parameters
end select

That said, things get pretty tedious quite quickly with this approach. Always using select type, distinguishing between numerous extending types, will be quite a bind. An alternative would be to ensure that the declared type base_pars has a binding whoami. Instead of changing the main program as above, we alter the module base_pars_module:

module base_par_modules
  implicit none  ! Encourage good practice

  type,abstract,public :: base_pars
   contains
    procedure(whoami_if), deferred :: whoami
  end type

  interface
    integer function whoami_if(this)
      import base_pars    ! Recall we're in a different scope from the module
      class(base_pars) this
    end function
  end interface

end module

So, we’ve a deferred binding in base_pars that is later over-ridden by a binding in the extending type test_pars. mask_test%parameters%whoami() in the main program is then a valid and the function called is that offered by the dynamic type of parameters.

Both approaches here address the problem with the binding of the declared type of parameters. Which best suits your real-world problem depends on your overall design.

If you know that your hierarchy of types will all have enough in common with the base type (that is, all will offer a whoami binding) then it makes sense to go for this second approach. Use the first approach rather when you have odd special cases, which I’d suggest should be rare.

Leave a Comment