Fortran模块中类型之间的循环依赖关系

时间:2016-04-27 08:36:37

标签: module fortran

我不知道Fortran模块中究竟是如何解析循环依赖关系的。以下模块使用ifort-2016和gfortran-4.9

进行编译
module types
   implicit none
   type type1
      type(type2), pointer :: t2
   end type type1

   type type2
      type(type1)          :: t1
      integer              :: x
   end type type2
end module

但如果我将定义顺序更改为

module types
   implicit none
   type type2
      type(type1)          :: t1
      integer              :: x
   end type type2

   type type1
      type(type2), pointer :: t2
   end type type1
end module

我收到以下错误

error #6457: This derived type name has not been declared.   [TYPE1]
      type(type1)          :: t1

行为与ifort-2016和gfortran-4.9相同。 由于两个模块中存在类似的循环依赖关系,为什么第一个编译但第二个不编译?

1 个答案:

答案 0 :(得分:5)

工作代码和不工作代码之间的区别在于具有组件的pointer属性的类型的位置。这个属性允许类型声明引用之前未定义的类型。

看看

type type2
  type(type1)          :: t1
  integer              :: x
end type type2

此处type1类型的type2组件不具有pointer属性。这意味着必须先前已定义类型type1。在你的第一个,工作,例子就是这样。在你的第二个,破碎的例子中,它不是。

看另一种类型

type type1
   type(type2), pointer :: t2
end type type1

type2组件具有指针属性。因此,在此引用之前不需要定义类型type2。您可以在两个示例中看到这一点。

此要求在Fortran 2008标准中声明为

  

C440(R436)如果既未指定POINTER也未指定ALLOCATABLE属性,则component-def-stmt中的declaration-type-spec应指定内部类型或先前定义的派生类型。

我这里只关注pointer属性。正如引用所暗示的那样,allocatable属性也是如此。允许此后用allocatable引用是Fortran 2008中的新增功能:在Fortran 2003中,需要pointer属性。正如Vladimir F所评论的那样,所有编译器都没有实现这种新的自由(提供递归可分配组件)。在上文中,在适当的位置阅读“pointerallocatable”。