Вы не первый, у кого возникла эта проблема, и я рад сообщить, что этот недостаток в стандарте будет исправлен в Fortran 2015. Как указано в в этом документе (стр. 6, заголовок«Одобренные изменения в стандарте»), «должно быть снято ограничение на появление оператора error stop
в процедуре pure
» .
Стандарт Fortran 2008 включалerror stop
утверждение в контексте некоторых новых возможностей параллельных вычислений.Он сигнализирует об ошибке и останавливает все процессы как можно скорее.В настоящее время ни stop
, ни error stop
операторы не разрешены в pure
процедурах, потому что они явно не поточнобезопасны.На практике это неоправданно ограничивает случаи, когда возникает внутренняя ошибка.
В зависимости от вашего компилятора, вам, возможно, придется терпеливо ждать реализации.Я знаю, что Intel реализовал в своем компиляторе ifort.( "F2015: отменить ограничение на STOP и ERROR STOP в процедурах PURE / ELEMENTAL" )
альтернатива
Для альтернативного подхода вы можете посмотреть на этот вопрос , хотя в вашем случае это, вероятно, немного сложнее, так как вам нужно изменить ключевое слово do concurrent
, а не просто pure
.
(конец правильного ответа)
если грязные руки - вариант ...
Тем временем вы могли бы сделать что-нибудь жестокое, как
pure subroutine internal_error(error_msg)
! Try hard to produce a runtime error, regardless of compiler flags.
! This is useful in pure subprograms where you want to produce an error,
! preferably with a traceback.
!
! Though far from pretty, this solution contains all the ugliness in this
! single subprogram.
!
! TODO: replace with ERROR STOP when supported by compiler
implicit none
character(*), intent(in) :: error_msg
integer, dimension(:), allocatable :: molested
allocate(molested(2))
allocate(molested(2))
molested(3) = molested(4)
molested(1) = -10
molested(2) = sqrt(real(molested(1)))
deallocate(molested)
deallocate(molested)
molested(3) = molested(-10)
end subroutine internal_error
Если кто-то спросит, вы не получите это от меня.