- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hello all,
I'm trying to figure out the PROCEDURE declaration and I can't get it to work. For example, with the module and main:
module proc_component_example
type t
real :: a
procedure(print_me), pointer, nopass :: proc
end_type t
contains
subroutine print_me (arg, lun)
type(t), intent(in) :: arg
integer, intent(in) :: lun
write (lun,*) arg%a
end subroutine print_me
subroutine print_my_square (arg, lun)
type(t), intent(in) :: arg
integer, intent(in) :: lun
write (lun,*) arg%a**2
end subroutine print_my_square
end module proc_component_example
program main
use proc_component_example
use iso_fortran_env, only :: output_unit
type(t) :: x
x%a = 2.71828
x%proc => print_me
call x%proc(x, output_unit)
x%proc => print_my_square
call x%proc(x, output_unit)
end program main
I get a compilation error #8169: The specified interface is not declared. [PRINT_ME]. If I add an interface, a la
interface print_me
module procedure print_me
end interface
I get another compilation error #8182: The name is neither an abstract interface nor a procedure with an explicit interface. [PRINT_ME].
If I add an abstract interface I get yet another error #6457: This derived type name has not been declared.
What am I missing?
Thanks
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Offhand, I think your example should work. I recall that I submitted a bug report about similar behavior recently, the bug is not yet fixed. However, the following works. Note the required IMPORT to make T visible in the interface. Also, the ordering of the declarations seems to matter (though I don't think it should.)
[cpp]module proc_component_example type t real :: a procedure(print_int), pointer, nopass :: proc end type t abstract interface subroutine print_int (arg, lun) import type(t), intent(in) :: arg integer, intent(in) :: lun end subroutine print_int end interface contains subroutine print_me (arg, lun) type(t), intent(in) :: arg integer, intent(in) :: lun write (lun,*) arg%a end subroutine print_me subroutine print_my_square (arg, lun) type(t), intent(in) :: arg integer, intent(in) :: lun write (lun,*) arg%a**2 end subroutine print_my_square end module proc_component_example program main use proc_component_example use iso_fortran_env, only : output_unit type(t) :: x x%a = 2.71828 x%proc => print_me call x%proc(x, output_unit) x%proc => print_my_square call x%proc(x, output_unit) end program main[/cpp]
Link Copied
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Offhand, I think your example should work. I recall that I submitted a bug report about similar behavior recently, the bug is not yet fixed. However, the following works. Note the required IMPORT to make T visible in the interface. Also, the ordering of the declarations seems to matter (though I don't think it should.)
[cpp]module proc_component_example type t real :: a procedure(print_int), pointer, nopass :: proc end type t abstract interface subroutine print_int (arg, lun) import type(t), intent(in) :: arg integer, intent(in) :: lun end subroutine print_int end interface contains subroutine print_me (arg, lun) type(t), intent(in) :: arg integer, intent(in) :: lun write (lun,*) arg%a end subroutine print_me subroutine print_my_square (arg, lun) type(t), intent(in) :: arg integer, intent(in) :: lun write (lun,*) arg%a**2 end subroutine print_my_square end module proc_component_example program main use proc_component_example use iso_fortran_env, only : output_unit type(t) :: x x%a = 2.71828 x%proc => print_me call x%proc(x, output_unit) x%proc => print_my_square call x%proc(x, output_unit) end program main[/cpp]
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Offhand, I think your example should work. I recall that I submitted a bug report about similar behavior recently, the bug is not yet fixed. However, the following works. Note the required IMPORT to make T visible in the interface. Also, the ordering of the declarations seems to matter (though I don't think it should.)
[cpp]module proc_component_example
type t
real :: a
procedure(print_int), pointer, nopass :: proc
end type t
abstract interface
subroutine print_int (arg, lun)
import
type(t), intent(in) :: arg
integer, intent(in) :: lun
end subroutine print_int
end interface
contains
subroutine print_me (arg, lun)
type(t), intent(in) :: arg
integer, intent(in) :: lun
write (lun,*) arg%a
end subroutine print_me
subroutine print_my_square (arg, lun)
type(t), intent(in) :: arg
integer, intent(in) :: lun
write (lun,*) arg%a**2
end subroutine print_my_square
end module proc_component_example
program main
use proc_component_example
use iso_fortran_env, only : output_unit
type(t) :: x
x%a = 2.71828
x%proc => print_me
call x%proc(x, output_unit)
x%proc => print_my_square
call x%proc(x, output_unit)
end program main[/cpp]
Thanks Steve,
I'd missed the import, I didn't think I needed it as t wasn't private. Also, what do you mean that the declaration order is important? My understanding is that the import will only make objects available that have been declared prior to the interface body. Is that what you mean?
Thanks again!
Rich
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
My comment wasn't in regard to IMPORT, but rather there seems to be a required order for the interface and its use in PROCEDURE. I don't think there should be an order - if an explicit interface is visible, then it should be usable. I think this is a compiler bug and will bring it to the attention of the developers.
The IMPORT is required in an interface block if you want any of the host symbols to be visible. See my blog post on IMPORT for more details.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content

- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page