Originally posted by: Rafik_Zurob
Last week, I wrote about user-defined constructors in Fortran 2003. This week, I'd like to discuss user-defined assignment bindings and their role as "copy constructors" for allocatable components.
Like Fortran 90's user-defined assignment interface blocks, Fortran 2003's user-defined assignment bindings define a set of subroutines the compiler must call to perform assignment between objects of two types. User-defined assignment bindings are treated differently from interface blocks when you have intrinsic assignment between types containing allocatable components. Consider the following program which defines an assignment binding for copying objects of type dt1 and a defined assignment interface block for copying objects of type dt2:
module m
implicit none
type dt1
integer :: data
contains
procedure assign_dt1
generic :: assignment(=) => assign_dt1
end type
type dt2
integer :: data
contains
procedure assign_dt2
end type
type container
type(dt1), allocatable :: d1
type(dt2), allocatable :: d2
end type
interface assignment(=)
module procedure assign_dt2
end interface
contains
subroutine assign_dt1(to, from)
class(dt1), intent(out) :: to
type(dt1), intent(in) :: from
to%data = from%data + 10
end subroutine
subroutine assign_dt2(to, from)
class(dt2), intent(out) :: to
type(dt2), intent(in) :: from
to%data = from%data + 10
end subroutine
end module
use m
implicit none
type(container) c1, c2
allocate(c1%d1, source=dt1(3))
allocate(c1%d2, source=dt2(4))
c2 = c1
print *, c2%d1
print *, c2%d2
end
As done last week, I'll use the functrace feature of XLF to show what's going on:
> xlf2003 assignment_binding_example.f -qfunctrace tracing_routines.o
** m === End of Compilation 1 ===
** _main === End of Compilation 2 ===
1501-510 Compilation successful for file assignment_binding_example.f.
> a.out
{ _main (assignment_binding_example.f:43)
{ __m_NMOD_assign_dt1 (assignment_binding_example.f:29)
} __m_NMOD_assign_dt1 (assignment_binding_example.f:30)
13
4
} _main (assignment_binding_example.f:48)
>
In the intrinsic assignment between variables c1 and c2, the assignment binding was called for the derived type assignment of c1%d1 to c2%d1. This is not done for user-defined assignment interface blocks. As a result, subroutine assign_dt2 was not called in this program, and intrinsic assignment was used for the derived type assignment of c1%d2 to c2%d2.