具有重载赋值的嵌套派生类型

时间:2013-09-28 06:38:50

标签: fortran fortran95 fortran2003

我有一个包含其他派生类型(wrapper)的派生类型(over)。对于后者,赋值运算符已经过载。由于派生类型的赋值按默认分组发生,我希望分配两个wrapper实例会在某个时刻调用over的重载赋值。但是,使用下面的程序似乎并非如此。仅当我还重载wrapper的赋值时,才会调用重载的赋值,over包含module test_module implicit none type :: over integer :: ii = 0 end type over type :: wrapper type(over) :: myover end type wrapper interface assignment(=) module procedure over_assign !module procedure wrapper_assign end interface assignment(=) contains subroutine over_assign(other, self) type(over), intent(out) :: other type(over), intent(in) :: self print *, "Assignment of over called" other%ii = -1 end subroutine over_assign !subroutine wrapper_assign(other, self) ! type(wrapper), intent(out) :: other ! type(wrapper), intent(in) :: self ! ! other%myover = self%myover ! !end subroutine wrapper_assign end module test_module program test use test_module implicit none type(wrapper) :: w1, w2 print *, "Assigning wrapper instances:" w2 = w1 end program test 实例之间的显式赋值(通过取消注释注释的代码行)。为什么?我发现它有点违反直觉。有没有办法避免包装类型的重载?

{{1}}

2 个答案:

答案 0 :(得分:9)

这种[不幸]情况是导出类型的内在分配的语言规则(F90 +)的结果。细节在F2008 7.2.1p13中详细说明。总而言之,派生类型的内在赋值(使用特定注释掉的wrapper_assign发生的赋值)不会为派生类型的任何组件调用非类型绑定定义的赋值。在F90 / F95中,如果要在组件层次结构的某个较低级别定义赋值,则需要为所有父组件定义分配,直到基础对象。

F2003为该语言添加了类型绑定定义的赋值,并且由派生类型的内在赋值调用此 。使用它代替指定已定义赋值的独立通用形式。 (这也避免了类型名称可访问但可能无法访问已定义的分配过程的潜在问题。)

答案 1 :(得分:1)

只是为了完成这个主题:IanH's suggestion的具体实现(请赞成他原来的答案而不是这个)对我有用的是:

module test_module
  implicit none

  type :: over
    integer :: ii = 0
  contains
    procedure :: over_assign
    generic :: assignment(=) => over_assign
  end type over

  type :: wrapper
    type(over) :: myover
  end type wrapper

contains

  subroutine over_assign(other, self)
    class(over), intent(out) :: other
    class(over), intent(in) :: self

    print *, "Assignment of over called"
    other%ii = -1

  end subroutine over_assign

end module test_module


program test
  use test_module
  implicit none

  type(wrapper) :: w1, w2

  print *, "Assigning wrapper instances:"
  w2 = w1

end program test