模块和类型绑定过程

时间:2012-06-18 07:25:09

标签: types fortran

我收到以下错误消息:

The name of the module procedure conflicts with a name
in the encompassing scoping unit.   [ADD_SUB]

ifort 12.0.3 64位平台上使用ubuntu 12.04编译下面的源代码时。

任何想法?

Module Header

  Type :: hello

      Integer :: a
      Integer :: b    
      Integer :: sum

    contains

      procedure, pass :: add => add_sub

  End type hello

  Interface

    Subroutine add_sub(this)
       Import hello
       Implicit None
       class(hello) :: this

    End Subroutine add_sub

  End Interface

End Module


Module Routines

  use Header

contains

  Subroutine add_sub(this)    
    Implicit None    
    class(hello), intent(inout) :: this
    this%sum=this%a+this%b    
  End Subroutine

End Module



Program Test

  use Header    
  use Routines

  Implicit None

  Type(hello) :: x

  x%a=1    
  x%b=2

  call x%add()

  write(*,*) x

End Program Test

2 个答案:

答案 0 :(得分:1)

我认为您遇到的问题是,由于Fortran编译器为所有模块过程提供了显式接口,因此编译器会在程序add_sub的最顶层范围内找到test的两个实例。

我已经查看了Fortran 2003标准,并且无法立即找到禁止您所做的事情的规则。但是,这很不寻常。将常规声明和定义放在单独的编译单元中的冲动似乎比使用普通的Fortran程序员更多地影响了C / C ++程序员。

如果你想在编码中分开这些,我认为你有以下选择:

  • 将子例程定义放入不是模块的编译单元中。例如,我可以通过删除模块routines并在其自己的编译单元中使用子例程add_sub来编译程序片段。
  • 使用include语句包含定义例程的源文件的文本。
  • 等待编译器实现Fortran 2008的submodule功能。

我并不认为这是一个特殊的问题,我是那些普通的Fortran程序员之一,他们习惯于将类型绑定程序的整个定义放在同一个编译单元中。声明它们受约束的类型。

有可能,请注意,Fortran标准并不禁止您执行您尝试执行的操作,但英特尔编译器尚未实现该功能,或者未正确实现该功能。为什么不通过他们的技术支持人员,他们通常都很好。

答案 1 :(得分:0)

您已经定义了例程add_sub两次,并且名称相互冲突。这可以通过在模块Header的开头添加以下行来轻松解决:

private add_sub

这使得add_sub的定义对模块是私有的,因此任何导入模块的例程都无法直接访问它 - 相反,它们将通过公共接口add