For Programmers: Free Programming Magazines  


Home > Archive > Fortran > May 2005 > Q: GO TO the CONTINUE of a DO loop









You are viewing an archived Text-only version of the thread. To view this thread in it's original format and/or if you want to reply to this thread please [click here]

 

Author Q: GO TO the CONTINUE of a DO loop
Ryo

2005-05-17, 8:59 am

Hello all,

I've come across a code where there are jumps to
the terminal statements of DO loops, and I'm wondering
what they do, according to the standard.

(1)
do 100 i = 1, 10
. . . . . .
if (. . .) go to 100
. . . . . .
100 continue

If it conforms to the standard, is this equivalent with

(2)
do 100 i = 1, 10
. . . . . .
if (. . .) go to 999 !! EXIT
. . . . . .
100 continue
999 continue

or

(3)
do 100 i = 1, 10
. . . . . .
if (. . .) go to 999 !! CYCLE
. . . . . .
999 continue
100 continue

? (I hope (2) and (3) are standard-conforming. :)

Even in the days of F77, I had never written code like (1)
because I didn't know how to interpret it, and even if I did
know, I wouldn't have thought the reader of my code would
always know.

I'm sure this is a FAQ, but I didn't find relevent discussion
in google (too many hits with keywords like "go to", "continue",
"do loop"). I also tried to decipher the F77 standard
(http://www.fortran.com/fortran/F77_std/rjcnf.html) but I didn't
find a clue by browsing the sections of DO and GO TO.

Thank you,
Ryo

glen herrmannsfeldt

2005-05-17, 8:58 pm

Ryo wrote:

> I've come across a code where there are jumps to
> the terminal statements of DO loops, and I'm wondering
> what they do, according to the standard.


> (1)
> do 100 i = 1, 10
> . . . . . .
> if (. . .) go to 100
> . . . . . .
> 100 continue


> If it conforms to the standard, is this equivalent with


(snip of examples with GOTOs going to a statement just before
and just after the loop terminating CONTINUE.)

> ? (I hope (2) and (3) are standard-conforming. :)


You didn't give the hard cases, which are also legal:

do 100 i = 1, 10
do 100 j = 1, 10
. . . . . .
if (. . .) go to 100
. . . . . .
100 continue

and:

do 100 i = 1, 10
. . . . . .
if (. . .) go to 100
. . . . . .
100 a(i)=x

I believe one relevant part of the standard, from 8.1.6.2:

The range of a nonblock DO construct consists of the do-body
and the following DO termination. The end of such a range is
not bounded by a particular statement as for the other executable
constructs (e.g., END IF); nevertheless, the range satisfies the
rules for blocks (8.1.1). Transfer of control into the do-body or
to the DO termination from outside the range is prohibited; in
particular, it is permitted to branch to a do-term-shared-stmt
only from within the range of the corresponding
inner-shared-do-construct.

That is, the terminating statement is part of the range of the DO,
and so the GOTO does not exit the loop early.

(I wonder if this is the source of the C continue statement
which starts the next iteration of a loop early.)

In the case of a statement terminating more than one DO loop it is
inside the range of both loops. In the case of a statement other
than CONTINUE terminating a DO loop, that statement is executed as
part of the body of the loop, before the next iteration.

Just one more example, which I do believe is illegal:

do 100 i = 1, 10
. . . . . .
if (. . .) go to 100
. . . . . .
do 100 j = 1, 10
. . . . . .
100 continue

In this case, the GOTO would be going into the range of the j
loop from outside, and so would be illegal.

(and I won't mention extended range of DO loops, already
gone in Fortran 77)

-- glen

Richard E Maine

2005-05-17, 8:58 pm

In article <NK2dnT1YKMwH3xffRVn-qA@comcast.com>,
glen herrmannsfeldt <gah@ugcs.caltech.edu> wrote:

> Just one more example, which I do believe is illegal:
>
> do 100 i = 1, 10
> . . . . . .
> if (. . .) go to 100
> . . . . . .
> do 100 j = 1, 10
> . . . . . .
> 100 continue
>
> In this case, the GOTO would be going into the range of the j
> loop from outside, and so would be illegal.


You are correct that this is illegal (though in my first skim, I missed
the important first 2 letters of the word "illegal").

However, I'll note that I have worked with old programs that used this
abominable and nonstandard practice. I've had to help convert said
programs so that they actually compiled and worked correctly on
compilers that didn't support this as an extension. Painful. My pains
were exacerbated by the problem that the compiler I was working with at
the time didn't give an error message for it either - it just compiled
it without warning into code that didn't do anything sensible.

What once somewhat upset me was that it took quite a lot of work to
explain to a particular compiler vendor representative that this wasn't
standard. That discussion took place on this newsgroup (somewhere around
2 decades ago). I'll avoid names even though the particular rep hasn't
been here in an age (and the vendor in question is still around but
seems close to going under IMO :-)). It turns out that the vendor rep
had assumed that he knew what the rage of a DO loop meant. Simple enough
concept, right? Except that his definition didn't match the one in the
standard. IIRC, he thought that DO loop ranges were non-overlapping so
that the range of a DO loop excluded the ranges of any nested loops, or
some such thing. It didn't actually hold together as a consistent
definition, but that's what lead him down the wrong road.

--
Richard Maine | Good judgment comes from experience;
email: my first.last at org.domain | experience comes from bad judgment.
org: nasa, domain: gov | -- Mark Twain
glen herrmannsfeldt

2005-05-17, 8:58 pm

Richard E Maine wrote:

(snip of illegal GOTO to the terminating statement of a DO
from outside of that DO)

> You are correct that this is illegal (though in my first skim, I missed
> the important first 2 letters of the word "illegal").


> However, I'll note that I have worked with old programs that used this
> abominable and nonstandard practice. I've had to help convert said
> programs so that they actually compiled and worked correctly on
> compilers that didn't support this as an extension. Painful. My pains
> were exacerbated by the problem that the compiler I was working with at
> the time didn't give an error message for it either - it just compiled
> it without warning into code that didn't do anything sensible.


(snip)

One I remember seeing once was an FFT routine that had many nested DO
loops from 1 to 2, for the radix 2 transform. There were then IF
statements to enter the appropriate inner DO, and exit before the
termination of that DO. Most likely illegal, but it might work if
the compiler doesn't optimize too much. Leaving out the IF around
the termination, even though it is only CONTINUE statements, seems
much more likely to fail.

Definitely NOT extended range of the DO.

-- glen

FJRA

2005-05-18, 4:01 am

Hi, I tried myself in two compilers (compaq and g95), and get the
expected result:

do 100 i = 1, 2
goto 100
do 100 j = 3, 4
100 write(*,*) i, j

is illegal.


do 100 i = 1, 2
do 100 j = 3, 4
goto 100
100 write(*,*) i, j

is legal.

So, I have the question, can one say that the "100 write..." is inside
the inner loop, but not directly inside the outer loop?

Richard Maine

2005-05-18, 4:01 am

"FJRA" <a19980403@pucp.edu.pe> writes:

....
> do 100 i = 1, 2
> do 100 j = 3, 4
> goto 100
> 100 write(*,*) i, j

....
> So, I have the question, can one say that the "100 write..." is inside
> the inner loop, but not directly inside the outer loop?


Well... I suppose that one can say many things, and I wouldn't call
that incorrect. I just don't think that "directly inside" is a very
useful concept here. It is inside both loops - that part is easy.
The standard's technical term is "in the range of", but I'd accept
"inside" as a decent informal shorthand for that. I just can't think
of a place where one would use the concept of "directly inside"
very well. But if you find the concept useful (and perhaps define
it as meaning inside, but not inside of a nested loop), then I'd
agree with your application of that definition to this question.

Do loops like this to be confusing in subtle ways. The problem is with
ending on statements that actually "do" something, as opposed to
continue or enddo, which just mark the end of the loop.

To me the confusing part is that the statement label sort of stands
for two different places. If you goto the statement label, then you
are going to a point before that statement; the write (in this case)
gets executed after the goto. But in its role as a DO loop end, the
100 in some sense stands for a position after the write statement.

If the DO loop ends with a continue or enddo, then there basically
isn't anything to execute between the beginning of the statement and
the end of it, so the two points are the same.... if that makes sense
to anyone other than me.

Do/enddo is so much conceptually simpler. A little more verbose, yes,
but conceptually simpler.

--
Richard Maine
email: my last name at domain
domain: summertriangle dot net
Sponsored Links







Also available: Server administration forum archive | Web Design forum archive | Software forum archive | Hardware reviews archive

Copyright 2008 codecomments.com