【发布时间】:2018-11-15 23:50:30
【问题描述】:
我正在尝试拥有一个通用子例程 event() 和一个指向该通用子例程 event_i 的过程指针。然后我想创建任何子例程(如以下代码中的 hello_wolrd)并指向这个创建的子例程。你能帮我理解为什么第一个代码不起作用而第二个代码起作用吗?我在第一个版本的代码中得到的错误是:Program received signal SIGSEGV: Segmentation fault - invalid memory reference。我想使用第一个版本,因为这样我可以在子程序 hello_world 中使用 main 中定义的任何变量,而在第二种情况下,我必须将变量传递给 te 子程序,它不能再被定义为通用子程序 event() , 没有输入。
第一个版本(不工作)
program foo
implicit none
interface
subroutine event()
end subroutine event
end interface
procedure(event), pointer :: event_i => Null()
event_i => hello_world
call event_i
contains
subroutine hello_world()
print *, 'hello_world'
end subroutine
end program foo
第二版(工作):
program foo
implicit none
interface
subroutine event()
end subroutine event
subroutine hello_world()
end subroutine hello_world
end interface
procedure(event), pointer :: event_i => Null()
event_i => hello_world
call event_i
end program foo
subroutine hello_world()
print *, 'hello_world'
end subroutine
我用的是gfortran,编译器版本是
gfortran --version
GNU Fortran (Ubuntu 5.4.0-6ubuntu1~16.04.9) 5.4.0 20160609
【问题讨论】:
-
第一个版本不工作(给我分段错误),第二个版本正常工作。对于不清楚的问题,我深表歉意。
-
欢迎使用 Stack Overflow。 从不说“它不起作用”或“它不起作用”,真的从不。说出实际发生的事情。它会崩溃吗?它会给出错误的结果吗?它是如何崩溃的?任何错误信息?哪个确切的消息?哪些确切的错误结果以及好的结果应该是什么样子?
-
你是对的,我们可能没有得到真正的代码。当然,这是一个问题。 @fdevita 请创建一个minimal reproducible example,我们可以自己测试并真正编译。
-
我已经修复了打印语句中未终止字符的错误,添加了第一个版本给出的错误并指定了编译器版本。
-
因此,如果需要使用 WSL,似乎必须避免使用 Fortran 2008 的这一特性。根据groups.google.com/d/msg/comp.lang.fortran/6qUqEl8CIoc/… Windows 上的英特尔 Fortran 可能使用不同的机制。此解释适用于 GCC 中的 C 嵌套函数,但对 gfortran stackoverflow.com/a/33357450/721644 仍然有效
标签: pointers fortran procedure windows-subsystem-for-linux