我想将fortran write-statement包装在自定义子例程或函数中,其中包含一些额外的调试逻辑。
但我目前仍然坚持定义函数/子程序的原型。 这可能吗?如果是,怎么样?
答案 0 :(得分:3)
你的问题的标题表现出误解,尽管文本表明你知道的更好。然而,对于记录,write
是Fortran语句,它既不是子例程也不是函数。
我认为你有很多选择。我偶尔使用的一种方法是编写一个返回字符串的函数。也许
function error_message(error)
character(len=*), intent(in) :: error
character(len=:), allocatable :: error_message
error_message = 'ERROR: '//trim(error)
end function error_message
然后可以像这样使用
write(*,*) error_message('Oh s**t')
您当然可以编写子程序或带副作用的函数,包括写入输出通道,但如果采用这种方法,则必须小心遵守递归i / o的规则。
修改
OP发表评论后。
如果要关闭调试消息,可以使用另一个选项将它们指向空设备或文件,例如Linux上的/dev/null
或Windows上的NUL
。像
integer, parameter :: debug_channel = 99
logical, parameter :: debugging = .false.
...
if (debugging) then
open(debug_channel, file='NUL')
else
open(debug_channel, file='debuglog'
end if
然后
write(debug_channel,*) 'message'
答案 1 :(得分:1)
完成大部分内容的一种相对简单的方法是简单地将if
内联到每个受调试控制的写入前面:
if(debug)write(..,..)..
其中debug是全局逻辑值,甚至是:
if(debugf(level))write(..,..)..
其中逻辑函数debugf根据某个参数确定是否写入。
答案 2 :(得分:0)
除了其他答案之外,您可以避免将if (debug) write...
与派生类型IO一起使用。
我说“可能”,因为它非常愚蠢,除非你已经有了合适的结构,目前很少有编译器支持。
但是,作为一个例子,用ifort 14.0.1编译:
module errormod
type error_t
character(len=:), allocatable :: message
contains
procedure write_error
generic :: write(formatted) => write_error
end type error_t
logical debug_verbose
contains
subroutine write_error(err, unit, iotype, v_list, iostat, iomsg)
class(error_t), intent(in) :: err
integer, intent(in) :: unit
character(len=*), intent(in) :: iotype
integer, intent(in), dimension(:) :: v_list
integer, intent(out) :: iostat
character(len=*), intent(inout) :: iomsg
if (debug_verbose) then
write(unit, '("Error: ", A)', iostat=iostat, iomsg=iomsg) err%message
else
write(unit, '()', advance='no')
end if
end subroutine write_error
end module errormod
program test
use errormod
implicit none
type(error_t) error
debug_verbose = .TRUE.
error%message = "This error will be reported."
write(*, '(dt)') error
debug_verbose = .FALSE.
error%message = "This error will not be reported."
write(*, '(dt)') error
debug_verbose = .TRUE.
error%message = "This final error will also be reported."
write(*, '(dt)') error
end program test
将显示第一条和第三条消息,但不会显示第二条消息。