Methods in Fortran

Fortran supports procedures defined on derived types, which are similar to methods in object-oriented programming languages.

module rect_module
  implicit none
  
  type :: rect
    integer :: width, height
  end type rect

  contains
  
  ! This area function is associated with the rect type
  function area(r) result(res)
    type(rect), intent(in) :: r
    integer :: res
    res = r%width * r%height
  end function area

  ! This perim function is also associated with the rect type
  function perim(r) result(res)
    type(rect), intent(in) :: r
    integer :: res
    res = 2*r%width + 2*r%height
  end function perim
end module rect_module

program main
  use rect_module
  implicit none
  
  type(rect) :: r
  r = rect(width=10, height=5)

  ! Here we call the 2 functions defined for our derived type
  print *, "area: ", area(r)
  print *, "perim:", perim(r)

  ! Fortran doesn't have pointers to derived types in the same way as some other languages,
  ! but we can use the `target` attribute and pointer variables if needed
  type(rect), target :: r_target
  type(rect), pointer :: rp

  r_target = rect(width=10, height=5)
  rp => r_target

  print *, "area: ", area(rp)
  print *, "perim:", perim(rp)
end program main

To run the program, save it as methods.f90 and compile it using a Fortran compiler:

$ gfortran methods.f90 -o methods
$ ./methods
 area:           50
 perim:          30
 area:           50
 perim:          30

In Fortran, we use modules to group related derived types and their associated procedures. This is similar to the concept of structs and methods in other languages.

Fortran doesn’t have receiver types in the same way as some object-oriented languages. Instead, we define functions that take the derived type as an argument. These functions are often referred to as type-bound procedures when they are associated with a derived type.

Fortran also doesn’t automatically handle conversion between values and pointers for function calls in the same way. If you need to work with pointers, you need to explicitly declare them and use the target attribute on the original variable.

Next, we’ll look at Fortran’s mechanism for abstracting and generalizing code: interfaces and abstract types.