- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
Hi, I'm wondering if there exists a way (other than branching) for exiting or cycling within a inner block in a do block:
...
do i=1,10
block
integer :: k
...
if (...) then
...
cycle !not possible
end if
...
end block
end do
More general, the question is, if its possible to terminate the execution of a block-construct without using IF/GOTO? I've looked into the standard but I've found no other possibilities...
IMO such a feature would be especially usefull in combination with DO CONCURRENT and the need of iteration local variables.
Thanks
- Etiquetas:
- Intel® Fortran Compiler
Enlace copiado
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
Is this what you had in mind?
program test
implicit none
integer :: i
DOXYZ: do i=1,10
block
integer :: k
k=-100
if (mod(i,3).eq.0) then
k=i*i+1
write(*,*)'For i = ',i,', k set to ',k,', cycling'
cycle DOXYZ
end if
end block
write(*,*)'Block ended with i = ',i
end do DOXYZ
end program
If not, and you really want CYCLE and EXIT to apply to just the block and not to the entire loop body, I don't know what the meaning of CYCLE should then be, because the block is not by itself a construct for repetition. Similarly, allowing EXIT to exit the block construct would give that construct a facility that is not provided in the older IF ... THEN ... ELSE...ENDIF construct.
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
Not sure I too understand what exactly you mean by CYCLE an inner block - if you want to cycle, why not make the inner block a DO loop also?
Anyways, note EXIT statement is supported in BLOCK construct per Fortran 2008 standard and if I'm not mistaken (Intel can confirm), this feature will be available in Intel Fortran starting with 16.0 release (you can test it in 16.0 beta). See a use for it in a branch prediction pattern in message#5 of this thread: https://software.intel.com/en-us/forums/topic/516000.
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
Thanks for your answer!
Hmm strange...
Okay I've tested your example and it works even without the use of a label. In my particular code I'm using it within a module procedure and for some curious reason the compiler gives me the error message:
error #6604: The construct name in the CYCLE statement does not match any DO construct to which the CYCLE statement belongs. [DOXYZ]
cycle DOXYZ
--------------------------^
without the label:
error #6602: A CYCLE or EXIT statement must not be used with a non-DO block.
cycle
--------------------^
Maybe a bug? I'm using ifort 16.0 beta
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
We would have to see the full context (module source code, complete) to reproduce and understand what the compiler is saying.
My example code has just a single loop, so the label XYZ is not needed. However, if you had two nested DO loops, you might need labels if you wanted the CYCLE inside the BLOCK construct to cycle the outer DO loop rather than the inner DO loop.
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
When I modify your example, so that I would only exit the block and not the loop and change the DO to a DO CONCURRENT:
program test
implicit none
integer :: i
do concurrent (i=1:10)
block
integer :: k
k=-100
if (mod(i,3).eq.0) then
k=i*i+1
write(*,*)'For i = ',i,', k set to ',k,', cycling'
exit
end if
end block
write(*,*)'Block ended with i = ',i
end do
end program
I get the error message:
error #8432: An EXIT statement shall not belong to a DO CONCURRENT construct.
exit
------------^
So the exit statement gets associated with the do-construct and not with the block-construct. I'm not sure if a block-construct even understands the exit command. The standard says:
6 2 An EXIT statement belongs to a particular construct. If a construct name appears, the EXIT statement belongs 7 to that construct; otherwise, it belongs to the innermost DO construct in which it appears.
If I name the block:
program test
implicit none
integer :: i
do concurrent (i=1:10)
DOXYZ: block
integer :: k
k=-100
if (mod(i,3).eq.0) then
k=i*i+1
write(*,*)'For i = ',i,', k set to ',k,', cycling'
exit DOXYZ
end if
end block DOXYZ
write(*,*)'Block ended with i = ',i
end do
end program
I get the error:
error #8490: Transfer of control to the interior of this block from outside the block is prohibited. [LA]
Buuh, that seems all too strange to me...
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
Both of those from post 6 look like compiler bugs to me. I will escalate them to development. Issue ID is DPD200372670.
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
The first compiler error from post 6 might actually not be a bug: As quoted above, the standard says, that a exit statement gets automatically associated with the innermost loop when a name is omitted, even though the standard also prohibits the use of an exit statement in combination with a do concurrent loop...
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
You're right - I had not noticed that. This rule needed to be added to prevent changing the meaning of F2003-compliant code. Thanks.
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
Regarding #8
I see nothing inherently wrong with an exit in a DO CONCURRENT because it is the responsibility of the programmer to make sense of what happens due to the discrepancies resulting from the loop actually being performed concurrently (multiple threads), concurrently (multiple vector lanes) or sequentially.
As an approximate equivalent, assume an array of random data, where you use a parallel do to perform a search, or DO CONCURRENT to perform the search. Where any of the concurrencies that can find a match can exit and cause the other concurrencies to exit, with the caveated that the first match temporally found is not necessarily the match returned (race condition), nor is the match returned necessarily the same as that returned had the array been searched sequentially. The programmer assumes the responsibility to sort this out.
Parallel do does not have this capability, neither does do concurrent, but you can start a parallel region, split the array into sections, have each thread search the section using a for loop, and if found a match, inform all threads a match was found (thus causing the additional threads to abort their search). This is not an unusual circumstance, and I see no reason why exit cannot be treated in this way.
This said, there are too many other programmers, not willing to take on the responsibility, and wanting the compiler to say "can't do that". IMHO this this should be a warning, not an error.
Jim Dempsey
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
I forgot to add an additional 2 cents
Inside the DO CONCURRENT and inside the PARALLE DO it is perfectly acceptable to have a STOP statement, which essentially forces all concurrencies to exit, not only the loop but the process as well.
Jim Dempsey
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
The bug will be fixed in 16.0 Update 1.
- Marcar como nuevo
- Favorito
- Suscribir
- Silenciar
- Suscribirse a un feed RSS
- Resaltar
- Imprimir
- Informe de contenido inapropiado
Thanks!
- Suscribirse a un feed RSS
- Marcar tema como nuevo
- Marcar tema como leído
- Flotar este Tema para el usuario actual
- Favorito
- Suscribir
- Página de impresión sencilla