2012-06-29 56 views
4

對於Fortran中的擴展類型,應通過對不同模塊中的類型擴展可見的私有組件。Fortran擴展類型在不同模塊中

與這兩個gcc4.7和ifort在錯誤下面的代碼的結果,因爲BNAME是在兩個初始型和擴展。但是由於它是私人的,所以在不同模塊的擴展中不可訪問,即,如果在bar_type中註釋掉bName,則會出現它是私有的錯誤。

module foo 
    type :: foo_type 
    character(256),private :: bName = "foo" 
    contains 
    procedure :: pName => pName 
    end type 
contains 
    subroutine pName(this) 
    class(foo_type), intent(in) :: this 
    print*,trim(this%bName) 
    end subroutine 
end module 

module bar 
    use foo, only : foo_type 
    type,extends(foo_type) :: bar_type 
    character(256),private :: bName = "bar" 
    contains 
    procedure :: pName => pName 
    end type 
contains 

    subroutine pName(this) 
    class(bar_type), intent(in) :: this 
    print*,this%bName 
    end subroutine 
end module 


program test 
    use foo, only : foo_type 
    use bar, only : bar_type 
    type(foo_type) :: foo_inst 
    type(bar_type) :: bar_inst 

    call foo_inst%pName() 
    call bar_inst%pName() 
end program 

如果bar_type被包含在同一模塊foo_type中,然後BNAME是從bar_type,即訪問,下面的代碼將編譯

module foo 
    type :: foo_type 
    character(256),private :: bName = "foo" 
    contains 
    procedure :: pName => pName 
    end type 

    type, extends(foo_type) :: baz_type 
    contains 
    procedure :: pName => pName_baz 
    end type 
contains 
    subroutine pName_baz(this) 
    class(baz_type), intent(in) :: this 
    print*,trim(this%bName) 
    end subroutine 

    subroutine pName(this) 
    class(foo_type), intent(in) :: this 
    print*,trim(this%bName) 
    end subroutine 
end module 

program test 
    use foo, only : foo_type,baz_type 
    type(foo_type) :: foo_inst 
    type(baz_type) :: baz_inst 

    call foo_inst%pName() 
    call baz_inst%pName() 
end program 

一直有一個很難解析標準就知道在第一個例子中應該發生什麼。

+0

嗨,傑里米。我有完全相同的問題。你有沒有想過如何在不同的模塊中分離基類和派生類型以及訪問派生成員中的私有基類成員?謝謝。 – FortCpp

回答

2

我相信第一個例子是不符合標準的。

即使私有屬性使得bName無法訪問外模塊foo,它仍然是由bar_type繼承了組件(也許,而不是毫無意義的,因爲沒有什麼可以用它做,但是這不是問題) - 見注4.51在F2003 :

父類型的不可訪問組件和綁定也是繼承的,但它們在擴展類型中仍然不可訪問 。如果要擴展的類型通過 使用關聯訪問且具有私有實體,則會發生無法訪問的實體。

所以bar_type有名爲bName,這使得它的錯誤該名稱(見範圍和名稱規則第16.2)要添加其他成分的繼承組件。