我想定义一个子程序,它在输入上有一个无限多态指针数组。 三个步骤中的简化问题(问题出现在步骤3中):
1。 对于单个指针,可以这样做:
module def
type :: type1
real :: x
end type
type :: type2
real(8) :: y
end type
type(type1),target :: a
type(type2),target :: b
class(*),pointer :: p
contains
subroutine printer(p)
class(*),pointer :: p
select type(p)
type is (type1)
print*,p%x
type is (type2)
print*,p%y
end select
end subroutine
end module
program test
use def
a%x=3e0
b%y=5d0
p=>a
call printer(p)
p=>b
call printer(p)
end program
2。
如果我想将它推广到指针数组,我需要定义一个包含我的指针的类型并定义派生类型的数组。所以在第一步中我定义了我的类型并再次尝试了一个指针。在这里,我意识到我需要在associate
构造的子程序中使用select type
名称,而其余部分则直接向前延伸:
module def
type :: type1
real :: x
end type
type :: type2
real(8) :: y
end type
type(type1),target :: a
type(type2),target :: b
type point
class(*),pointer :: p
end type
type(point) :: p
contains
subroutine printer(z)
class(point) :: z
associate (o=>z%p)
select type(o)
type is (type1)
print*,o%x
type is (type2)
print*,o%y
end select
end associate
end subroutine
end module
program test
use def
a%x=3e0
b%y=5d0
p%p=>a
call printer(p)
p%p=>b
call printer(p)
end program
3。 但是,如果我现在定义所需的无限多态指针数组并相应地更改我的子程序,如下所示:
module def
type :: type1
real :: x
end type
type :: type2
real(8) :: y
end type
type(type1),target :: a
type(type2),target :: b
type point
class(*),pointer :: p
end type
type(point) :: p(1:2)
contains
subroutine printer(z)
class(point),dimension(1:) :: z
integer :: j
associate (o=>z%p)
do j=1,size(z,1)
select type(o)
type is (type1)
print*,o(j)%x
type is (type2)
print*,o(j)%y
end select
end do
end associate
end subroutine
end module
program test
use def
a%x=3e0
b%y=5d0
p(1)%p=>a
p(2)%p=>b
call printer(p)
end program
我收到错误:
associate (o=>z%p)
1
Error: Component to the right of a part reference with nonzero rank must not have the POINTER attribute at (1)
我理解错误,指针数组不是fortran标准的一部分。但目前我没有看到任何解决方法。如果没有这个associate
构造,我就无法进行类型选择,因为这会产生错误:
select type(z%p)
1
Error: Selector in SELECT TYPE at (1) is not a named variable; use associate-name=>
答案 0 :(得分:3)
就这样做
subroutine printer(z)
class(point),dimension(1:) :: z
integer :: j
do j=1,size(z,1)
select type(o=>z(j)%p)
type is (type1)
print*,o%x
type is (type2)
print*,o%y
end select
end do
end subroutine
该关联是select type
构造的一部分。
错误消息Error: Component to the right of a part reference with nonzero rank must not have the POINTER attribute at (1)
的说明:不允许以a%b
作为数组且a
为b
或allocatable
。
这是因为单个pointer
随机放置在内存中,而Fortran标准中的数组必须可以通过元素之间具有恒定步幅的描述符来描述。