Topic: A plea for goto without goto


Author: boukanov@sentef2.fi.uib.no (Igor Boukanov)
Date: 1997/03/22
Raw View
Consider the following code example,

  for (;;) {
    ...
    switch(selector) {
      case case1:
        ...
        break;
      ...
      case finish_loop:
         goto loop_end;
      ...
    }
    ...
  }
  loop_end: ...

This is a loop with a single terminate point, but nevertheless the code
to be efficient has to use goto. The solution without do not seems to be
more easily to read,

  for (;;) {
    ...
    bool finish_loop = false;
    switch(selector) {
      case case1:
        ...
        break;
      ...
      case finish_loop:
        finish_loop = true;
        break;
      ...
    }
    if (finish_loop) break;
    ...
  }

which rises the initial question again.


Regards, Igor Boukanov
igor.boukanov@fi.uib.no
http://www.fi.uib.no/~boukanov/
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: brad@cfar.umd.edu (Brad Stuart)
Date: 1997/03/18
Raw View
: My whole point is that we have, in fact, a single dimensioned array
: whose components are arrays.  We use find_if to iterator over the outer
: container (array), using a function class which iterates over the inner
: container as a predicate.

OK, I'll bite.

Given a 2D array A, we want to search for a row containing a zero
element. Since it might be useful to actually know the index of the
column, we make the searcher return it:

class aux_find
{
public:
  aux_find( int length, int target )
 : m_length(length), m_target(target) {}

  bool operator() ( int *start )
 // true when target is found
     {
 m_saved_idx = find( start, start+length, target ) - start;
        return ( m_saved_idx != m_length );
     }

  int saved_index() { return m_saved_idx; }

private:
  int m_length;
  int m_target;
  int m_saved_idx;
};

  int rows, columns;
  // ...
  int A[rows][columns];
  // ...

  aux_find searcher( columns, target );
  j = find_if( A, A+rows, searcher )) - A;
  i = searcher.saved_index();


I don't really like the business about stuffing the internal index
into the searcher, but maybe someone else can clean it up.  It does
work if the 2D array is non-contiguous.

Other possibilities include building aux_search out of binders and
other STL functors, and replacing the find_if with mismatch.

Brad

--
| Brad Stuart      brad@cfar.umd.edu
| Center for Automation Research
| University of Maryland, College Park
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Vik Heyndrickx <Vik.Heyndrickx@rug.ac.be>
Date: 1997/03/18
Raw View
I summarize the results till now of one week's discussion and add my
opinion. Everbody who added or will add constructive thoughts, thanks!

First of all, my intention was not to start a discussion whether it is
good programming practice to use goto's or not. This discussion has been
carried in the past and the results where that opponents do not agree.
Full stop. So if you're in favor of goto's, carry on using them.

It seems something alike has been done within other programming
languages [Dennis White].

An alternative was suggested in the past as was mentioned by [Bret
Pehrson]:
- Wasn't there talk of break taking a numeric parameter for the number
of levels to break from?
My primary intention is to make things easier for the programmer, I
think this does just the opposite (consider bigger loops)

Gerard Weatherby wrote:
>I'm going to postulate that code should be correct, easy to understand, and relatively efficient. I find goto's work against easy to understand.
I can't agree more.

>Extending the language with named breaks also works against easy to understand; this isn't so much because it's horribly complicated so much as it is yet another thing to understand about C++".
In my opinion it works in favour of easy to understand. And where is the
time that C only contained a few keywords.

Another solution by [Doug Murphy]:
> double anarray[13][7];
> unsigned x,y;
> for (y=0,x=0; x<7&&y<13; x<7?++x:(x=0,++y))
>     if(anarray[y][x]==0)
>         break;
  Cute, but...

Quite a lot of work-arounds within currently existing C++ standard have
been suggested in the replies:
- Use still goto's (with well chosen lable names put after the closing
"}") [Bryant Brandon]
Maybe acceptable when the loops are small, creats surveyability problems
with larger loops. You don't know for sure where the label is unless you
look for it. A break is a goto to the end of the loop. A continue is a
goto to the start.

- Put the loops into a(n inline) function and use return to simulate the
break. [Bill Seurer, Gerard Weatherby]
Is an acceptable and interesting solution, however creates a lot of
typing overhead and doesn't make things easier to understand for
beginning programmers.

- Use a second test identical to one in the nested loop in the outermost
loop [Jan Bielawski]
This creates typing overhead, therefore increases chance of mistakes and
the compiler may not be able to optimize the second test away,
especially when its a more complicated condition, resulting in less
efficient code. This is partly also the meaning of [David A. Cuthbert],
who also suggests to look at the result of a profiler whether this
significantly decreases the speed.
But what about platform independent source code?

Aren't these work-arounds just the proof there is something missing in
C/C++?

What concerns the argument "it can be done within the current
implementation of c++, why adding something to the syntax" consider
this:
Switch statements can be rewritten with goto's, as can all kind of
loops. Composed expression can be unfolded into simple expressions.
Finally we'll end up in ancient BASIC or assembler.

...It can be done, but either you choose to violate structured
programming policy, you insert code twice or the program's efficiency is
threatened...

To be continued...
---
[ comp.std.c++ is moderated.  To submit articles: Try just posting with your
                newsreader.  If that fails, use mailto:std-c++@ncar.ucar.edu
  comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
  Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
  Comments? mailto:std-c++-request@ncar.ucar.edu
]





Author: James Kanze <james-albert.kanze@vx.cit.alcatel.fr>
Date: 1997/03/18
Raw View
Christian Millour <chris161@mailhost.grolier.fr> writes:

|>  > It's important to recognize that in fact, there are two searches
|>  > involved.
|>
|>  not necessarily. In image processing this is viewed conceptually as
|>  one search, in a dataset that happens to be 2D. So the flattening of
|>  the loop may be a key conceptual issue. Especially when you might
|>  have to deal in the future with datasets having arbitrary numbers
|>  of dimensions.

Good point.  The most natural way to view the problem will depend on the
application field.

|>  I have consistently used flattened iterators with no adverse effect,
|>  although never on raw multidimensional arrays as above. What it bought
|>  me was an effortless transition from 2-D to N-D processing.
|>
|>  In this case I would use it as
|>
|>  bool zero_found;
|>  for (flattened_iterator i(anarray); !i.done(); i.advance())
|>    if ((zero_found = (i.current() == 0)))
|>      break;
|>
|>  I wonder whether a similar expression could be obtained with stl-style
|>  iterators.

With STL style iterators, certainly, although not directly with any
iterators already present in STL.  It is only a question of interface.

--
James Kanze      home:     kanze@gabi-soft.fr        +33 (0)1 39 55 85 62
                 office:   kanze@vx.cit.alcatel.fr   +33 (0)1 69 63 14 54
GABI Software, Sarl., 22 rue Jacques-Lemercier, F-78000 Versailles France
     -- Conseils en informatique industrielle --
---
[ comp.std.c++ is moderated.  To submit articles: Try just posting with your
                newsreader.  If that fails, use mailto:std-c++@ncar.ucar.edu
  comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
  Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
  Comments? mailto:std-c++-request@ncar.ucar.edu
]





Author: thegoat4@airmail.net (Bryant Brandon)
Date: 1997/03/19
Raw View
In article <332E7AF2.1A76@rug.ac.be>, Vik Heyndrickx
<Vik.Heyndrickx@rug.ac.be> wrote:

>I summarize the results till now of one week's discussion and add my
>opinion. Everbody who added or will add constructive thoughts, thanks!
>

[...]

>Quite a lot of work-arounds within currently existing C++ standard have
>been suggested in the replies:
>- Use still goto's (with well chosen lable names put after the closing
>"}") [Bryant Brandon]
>Maybe acceptable when the loops are small, creats surveyability problems
>with larger loops. You don't know for sure where the label is unless you
>look for it. A break is a goto to the end of the loop. A continue is a
>goto to the start.

   I had an afterthought about this.  To enhance the program's
readability, you could -- Ohmygosh! -- define a macro.

#define breakto goto
/* leave a comment to explain it if you'd like */

then

    double anarray[13][7];
    unsigned x,y;
    for (y=0;y<13;++y) {
        for (x=0;x<7;++x) {
            if(anarray[y][x]==0)
                goto vertical;
         } horizontal:;
    } vertical:;

would become

    double anarray[13][7];
    unsigned x,y;
    for (y=0;y<13;++y) {
        for (x=0;x<7;++x) {
            if(anarray[y][x]==0)
                breakto vertical;   //  <--- changed here
         } horizontal:;
    } vertical:;

which is a little more intuitive in big loops.

[...]

B.B.
---
[ comp.std.c++ is moderated.  To submit articles: Try just posting with your
                newsreader.  If that fails, use mailto:std-c++@ncar.ucar.edu
  comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
  Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
  Comments? mailto:std-c++-request@ncar.ucar.edu
]





Author: jbuck@Synopsys.COM (Joe Buck)
Date: 1997/03/20
Raw View
>: My whole point is that we have, in fact, a single dimensioned array
>: whose components are arrays.  We use find_if to iterator over the outer
>: container (array), using a function class which iterates over the inner
>: container as a predicate.

brad@cfar.umd.edu (Brad Stuart) writes:
>Given a 2D array A, we want to search for a row containing a zero
>element...

Ah, but any search over a 2D array must follow a sequential order.  You
could provide iterators that do row-by-row search or column-by-column
search, or even some kind of diagonal search if desired, making the 2D
container "look" 1-D.  Iterators can then define extra methods for
returning the current row, column, and matrix the iterator is pointing to.
We can then just use standard find or find_if algorithms.
--
-- Joe Buck http://www.synopsys.com/pubs/research/people/jbuck.html

Help stamp out Internet spam: see http://www.vix.com/spam/
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Gerard Weatherby <gerardw@alum.mit.edu>
Date: 1997/03/16
Raw View
Vik Heyndrickx wrote:
>
> Consider the next simple problem: search in a two-dimensional array the
> first element that is
> zero.
>
> In C++ this would become something like:
>
>   double anarray[13][7];
>   unsigned x,y;
>   for (y=0;y<13;++y)
>       for (x=0;x<7;++x)
>           if(anarray[y][x]==0)
>               goto zero_found;
>   zero_found:

This has been an interesting thread.

I'm going to postulate that code
should be correct, easy to understand, and relatively efficient. I
find goto's work against easy to understand.  Extending the language
with named breaks also works against easy to understand; this isn't so
much because it's horribly complicated so much as it is "yet another
thing to understand about C++".  The suggestions involving evaluation
terms or increment terms with the ? operator also make the code harder
to read than I'd generally care to deal with.

So my solution/suggestion is to go off in a different direction:

template <class T,int XLIMIT,int YLIMIT>
struct searchForZero {
     searchForZero(T anarray[XLIMIT][YLIMIT],unsigned &x,unsigned &y)
 {
 for (y=0;y<YLIMIT;++y)
     for (x=0;x<XLIMIT;++x)
  if (anarray[y][x]==0)
     return;
 }
};


int main( )
{
 double anarray[13][7];
 unsigned x,y;
 searchForZero<double,13,7>(anarray,x,y);
 cout << "x is " << x << ", y is " << y << endl;
}

So now you have a templated class which encapsulates the search for zero
concept, works for any scalar type of any dimensions, doesn't require
any break or goto.
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: jpotter@falcon.lhup.edu (John E. Potter)
Date: 1997/03/16
Raw View
James Kanze <james-albert.kanze@vx.cit.alcatel.fr> wrote:

> jpotter@falcon.lhup.edu (John E. Potter) writes:

> |>  for (;;) {
> |>   ...
> |>   if (someCondition)
> |>    break;  // or goto a label at end of loop
> |>   ...
> |>   }
> |>
> |>  This is a structured program.

> I don't think so.  Structured programming doesn't only require a single
> exit, it requires that the exit be at the bottom.

I think it requires exit _to_ the bottom, or we would need to reject
for and while which exit at the top and the then branch of if which
exits in the middle.  Let's add a couple of new reserved words to produce
the desired control structure.

    loop
        statement
    and_while (condition)
        statement

It is a very handy structure for things like Newton's method where a
new approximation must be calculated before the exit test can be made.
If the exit fails, the second statement resets things to prepare for
the next iteration in the first statement.  Just one example of loops
which always execute N + 1/2 times.

Just in case someone thinks this is a good idea, it is not a language
change proposal, just a demonstration of how it could be implemented
if we didn't already have ways to do it.

> Something like the above isn't too hard to follow in simple cases, but
> when the break ends up in the middle of some deeply nested construct, it
> can become confusing.

If the break is any place other than where I showed it, the program is
clearly unstructured since some other (nested) structure must have
more than one exit.  The same problem as the break N proposals and all
of the functions with multiple returns.

> |>  Let me put on my purist hat and solve your problem.  Searches have
> |>  empty bodies.  Any search with a non-empty body is messed up.
> |>
> |>   double anarray[13][7];
> |>   unsigned x,y;
> |>   for (y=0,x=0;y<13 && anarray[y][x] != 0;x==6?(x=0,++y):++x)
> |>    ;

> It's important to recognize that in fact, there are two searches
> involved.  In fact, a functional programmer (or someone well versed in
> STL?) would probably write it this way.  Someone from a procedural
> background will probably use nested loops, which are the procedural
> translation for tail recursive functions. (The two searches: you are
> looking for a column which contains a zero, and to determine whether the
> column contains a zero, you have a second search.)

> Anyone care to post the STL solution.  It should involve a find_if whose
> predicate is a function object doing a find.  I'm too lazy to work out
> the details, though.

An STL approach on sequences which will work for builtin array of
array, vector of vector, list of list?  Too much for me.  STL is
(wisely?) one dimensional.  Linearize it for the above problem:

    unsigned y(find(anarray[0], anarray[0] + 13 * 7, 0.0) - anarray[0]);
    unsigned x(y % 7);
    y /= 7;

I'm sure that this must be illegal and that it will work on most
implementations.  But it will not work on vector of vector nor list of
list.

John
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: boukanov@sentef2.fi.uib.no (Igor Boukanov)
Date: 1997/03/17
Raw View
Gerard Weatherby (gerardw@alum.mit.edu) wrote:
> So my solution/suggestion is to go off in a different direction:

> template <class T,int XLIMIT,int YLIMIT>
> struct searchForZero {
>      searchForZero(T anarray[XLIMIT][YLIMIT],unsigned &x,unsigned &y)
>  {
>  for (y=0;y<YLIMIT;++y)
>      for (x=0;x<XLIMIT;++x)
>   if (anarray[y][x]==0)
>      return;
>  }
> };


> int main( )
> {
>  double anarray[13][7];
>  unsigned x,y;
>  searchForZero<double,13,7>(anarray,x,y);
>  cout << "x is " << x << ", y is " << y << endl;
> }

Actually in gcc (but not in g++ !) you can do this in a more simple way
with the help of nested function.
int main() {
  double anarray[13][7];
  unsigned x,y;
  void searchForZero() {
    for (y=0;y<13;++y)
      for (x=0;x<7;++x)
        if (anarray[y][x]==0)
          return;
  }
  searchForZero();
  ...
}

Actually I find nested functions are quite nice feature especially for
an implementation of scientific algorithms. C++ versions that use separated
classes and passing all local variables via constructors look awful.

--
Regards, Igor Boukanov.
igor.boukanov@fi.uib.no
http://www.fi.uib.no/~boukanov/
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Christian Millour <chris161@mailhost.grolier.fr>
Date: 1997/03/17
Raw View
James Kanze wrote:
> jpotter@falcon.lhup.edu (John E. Potter) writes:
> |>  Let me put on my purist hat and solve your problem.  Searches have
> |>  empty bodies.  Any search with a non-empty body is messed up.
> |>
> |>      double anarray[13][7];
> |>      unsigned x,y;
> |>      for (y=0,x=0;y<13 && anarray[y][x] != 0;x==6?(x=0,++y):++x)
> |>              ;

I don't like the mixing of the 'found' and 'end of loop' tests. the
flattening is interesting though.

>
> It's important to recognize that in fact, there are two searches
> involved.

not necessarily. In image processing this is viewed conceptually as
one search, in a dataset that happens to be 2D. So the flattening of
the loop may be a key conceptual issue. Especially when you might
have to deal in the future with datasets having arbitrary numbers
of dimensions.

I have consistently used flattened iterators with no adverse effect,
although never on raw multidimensional arrays as above. What it bought
me was an effortless transition from 2-D to N-D processing.

In this case I would use it as

bool zero_found;
for (flattened_iterator i(anarray); !i.done(); i.advance())
  if ((zero_found = (i.current() == 0)))
    break;

I wonder whether a similar expression could be obtained with stl-style
iterators.
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: jpotter@falcon.lhup.edu (John E. Potter)
Date: 1997/03/17
Raw View
Gerard Weatherby (gerardw@alum.mit.edu) wrote:
: Vik Heyndrickx wrote:
: >   double anarray[13][7];
: >   unsigned x,y;
: >   for (y=0;y<13;++y)
: >       for (x=0;x<7;++x)
: >           if(anarray[y][x]==0)
: >               goto zero_found;
: >   zero_found:

: This has been an interesting thread.

: I'm going to postulate that code
: should be correct, easy to understand, and relatively efficient. I
: find goto's work against easy to understand.  Extending the language
: with named breaks also works against easy to understand; this isn't so
: much because it's horribly complicated so much as it is "yet another
: thing to understand about C++".  The suggestions involving evaluation
: terms or increment terms with the ? operator also make the code harder
: to read than I'd generally care to deal with.

I mostly agree with what you have said.  I am forced to reconsider the
readability of ?: even though one of the posts way mine.  The other
one was incorrect and it seems that no one even noticed, presumably
because it was not readable.  That was mentioned; so, someone must
have attempted to read it.

: So my solution/suggestion is to go off in a different direction:

: template <class T,int XLIMIT,int YLIMIT>
: struct searchForZero {
:      searchForZero(T anarray[XLIMIT][YLIMIT],unsigned &x,unsigned &y)
:     {
:     for (y=0;y<YLIMIT;++y)
:         for (x=0;x<XLIMIT;++x)
:         if (anarray[y][x]==0)
:            return;

//  return; // inserted by compiler

:     }
: };

6.6 Jump statements [stmt.jump]
break; continue; return expression[opt]; goto identifier;

So you see, unusual transfer of control can be spelled in four ways in
C++.  Note that in the above, the return could be replace by goto a
label at the end of function or break 2 if that were in the language.
No matter how you spell it, it is a jump out of the normal flow of
control.

IMHO, whether jumps are allowed in code is a matter which must be
decided in a shop, not in the standard.  None is easy to define,
while restricted use is much harder.  OTOH, concerns for the spelling
of jump border on the neurotic and should be taken up with a specialist
not the committee which has so far avoided practicing psychology without
a license.

Just for fun, I think the following avoids all things which have been
objected to.  I doubt that it is any clearer than the original goto,
but it is wholesome.  Well, at least no one has yet objected to short
circuited &&.

    y = 0;
    do
        for (x = 0; x < 7 && anarray[y][x] != 0.0; ++ x)
                //  have not finished row and this one doesn't fit
            ;
        while (x == 7 && ++ y < 13);
            // Didn't find one in this row and have more rows to check

John
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: James Kanze <james-albert.kanze@vx.cit.alcatel.fr>
Date: 1997/03/18
Raw View
jpotter@falcon.lhup.edu (John E. Potter) writes:

 |>  James Kanze <james-albert.kanze@vx.cit.alcatel.fr> wrote:
 |>
 |>  > jpotter@falcon.lhup.edu (John E. Potter) writes:
 |>
 |>  > |>  for (;;) {
 |>  > |>   ...
 |>  > |>   if (someCondition)
 |>  > |>    break;  // or goto a label at end of loop
 |>  > |>   ...
 |>  > |>   }
 |>  > |>
 |>  > |>  This is a structured program.
 |>
 |>  > I don't think so.  Structured programming doesn't only require a single
 |>  > exit, it requires that the exit be at the bottom.
 |>
 |>  I think it requires exit _to_ the bottom, or we would need to reject
 |>  for and while which exit at the top and the then branch of if which
 |>  exits in the middle.

In this case, I think that "top" and "bottom" refer to the lexical
structure, i.e.: when I finish the while/for, I go to the statement
immediately following them.

At any rate, your example violates the single exit principle for the
sequence block which composes the body of the loop.

 |>  Let's add a couple of new reserved words to produce
 |>  the desired control structure.
 |>
 |>      loop
 |>          statement
 |>      and_while (condition)
 |>          statement
 |>
 |>  It is a very handy structure for things like Newton's method where a
 |>  new approximation must be calculated before the exit test can be made.
 |>  If the exit fails, the second statement resets things to prepare for
 |>  the next iteration in the first statement.  Just one example of loops
 |>  which always execute N + 1/2 times.

The loop and a half has no good solution that I know of.  I've never
actually encountered in with mathematical approximations like Newton's
method, but I have in other contexts.  Most of the time I see it, it is
due to a lack of sufficient functional decomposition.  Most, however,
not all.

 |>  Just in case someone thinks this is a good idea, it is not a language
 |>  change proposal, just a demonstration of how it could be implemented
 |>  if we didn't already have ways to do it.
 |>
 |>  > Something like the above isn't too hard to follow in simple cases, but
 |>  > when the break ends up in the middle of some deeply nested construct, it
 |>  > can become confusing.
 |>
 |>  If the break is any place other than where I showed it, the program is
 |>  clearly unstructured since some other (nested) structure must have
 |>  more than one exit.  The same problem as the break N proposals and all
 |>  of the functions with multiple returns.

Even with the break where you show it, the sequence block which makes up
the body of the loop has two exits.

 |>  > |>  Let me put on my purist hat and solve your problem.  Searches have
 |>  > |>  empty bodies.  Any search with a non-empty body is messed up.
 |>  > |>
 |>  > |>   double anarray[13][7];
 |>  > |>   unsigned x,y;
 |>  > |>   for (y=0,x=0;y<13 && anarray[y][x] != 0;x==6?(x=0,++y):++x)
 |>  > |>    ;
 |>
 |>  > It's important to recognize that in fact, there are two searches
 |>  > involved.  In fact, a functional programmer (or someone well versed in
 |>  > STL?) would probably write it this way.  Someone from a procedural
 |>  > background will probably use nested loops, which are the procedural
 |>  > translation for tail recursive functions. (The two searches: you are
 |>  > looking for a column which contains a zero, and to determine whether the
 |>  > column contains a zero, you have a second search.)
 |>
 |>  > Anyone care to post the STL solution.  It should involve a find_if whose
 |>  > predicate is a function object doing a find.  I'm too lazy to work out
 |>  > the details, though.
 |>
 |>  An STL approach on sequences which will work for builtin array of
 |>  array, vector of vector, list of list?  Too much for me.  STL is
 |>  (wisely?) one dimensional.  Linearize it for the above problem:
 |>
 |>      unsigned y(find(anarray[0], anarray[0] + 13 * 7, 0.0) - anarray[0]);
 |>      unsigned x(y % 7);
 |>      y /= 7;
 |>
 |>  I'm sure that this must be illegal and that it will work on most
 |>  implementations.  But it will not work on vector of vector nor list of
 |>  list.

My whole point is that we have, in fact, a single dimensioned array
whose components are arrays.  We use find_if to iterator over the outer
container (array), using a function class which iterates over the inner
container as a predicate.

--
James Kanze      home:     kanze@gabi-soft.fr        +33 (0)1 39 55 85 62
                 office:   kanze@vx.cit.alcatel.fr   +33 (0)1 69 63 14 54
GABI Software, Sarl., 22 rue Jacques-Lemercier, F-78000 Versailles France
     -- Conseils en informatique industrielle --
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: "Dennis White" <whited@primenet.com>
Date: 1997/03/13
Raw View
> So, I propose a solution to this problem. Why not giving names to
> syntactical constructions, like loops? Those names then could be used as
> an argument to break or continue.

This has been done in several languages, one that I can think of and has
been around for a few years is REXX. Alot of those IBM'ers probably know
this one..

Anyways I didn't reply to this article to preach my unwilling knowledge of
a language but rather to clarify what I feel is the communities thoughts
towards goto.

I for one believe that goto has a place and time that it can be used,
however, too many times have I seen it in places that broke all the rules
of structured programming.

So from many years of reviews I by habit just cringe at thought of someone
using a goto and almost all the time have spoken against in the development
of software procedures and standards for development.

Anyways that's just my $0.02 worth...

Dennis White
whited@primenet.com
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: "Howard E. Hinant" <heh@beamtech.DOTcom>
Date: 1997/03/13
Raw View
Jan Bielawski wrote:

> I'm probably missing something but what's wrong with:
>
>         double anarray[13][7];
>         unsigned x,y;
>         for (y=0;y<13;++y) {
>             for (x=0;x<7;++x)
>                 if(anarray[y][x]==0)
>                     break;
>             if (x<7)
>                 break;
>         }

Efficiency and (this is more debatable) in my opinion, readability.

-Howard
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: jpotter@falcon.lhup.edu (John E. Potter)
Date: 1997/03/13
Raw View
Vik Heyndrickx (Vik.Heyndrickx@rug.ac.be) wrote:
: Consider the next simple problem: search in a two-dimensional array the
: first element that is
: zero.

: In C++ this would become something like:

:   double anarray[13][7];
:   unsigned x,y;
:   for (y=0;y<13;++y)
:       for (x=0;x<7;++x)
:           if(anarray[y][x]==0)
:               goto zero_found;
:   zero_found:

: Programmers that are rigorously against the use of goto will rewrite
: this by making use of a
: boolean variable.

Not everyone.

: Most of these people would accept the use of break

Not everyone.

: although this is a
: disguised goto, but one where the destination is well known, namely the
: instruction after the
: loop. Therefore it is acceptable in structured program.

Semi-structured program.  In single-entry single-exit (structured)
programming multiple extries and exits of loops and conditionals
are rejected.  In semi-structured programming, this is relaxed to
accept multiple exits from a loop.

for (;;) {
 ...
 if (someCondition)
  break;  // or goto a label at end of loop
 ...
 }

This is a structured program.  There is a single exit from the loop.
Structured has nothing to do with break/goto but how they are used.

: However in the
: case of a nested loop
: this is not possible because the break would only terminate the
: innermost loop.

Let me put on my purist hat and solve your problem.  Searches have
empty bodies.  Any search with a non-empty body is messed up.

 double anarray[13][7];
 unsigned x,y;
 for (y=0,x=0;y<13 && anarray[y][x] != 0;x==6?(x=0,++y):++x)
  ;

If you have a purist bothering you, this code should either make them
very happy or make them accept your goto.  If not, use goto.  Please
do not try to add yet another way to write semi-structured programs
to the language.

John
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Bret Pehrson <bretp@strata3d.com>
Date: 1997/03/13
Raw View
Vik Heyndrickx wrote:
[text follows]

Wasn't there talk of break taking a numeric parameter for the number of
levels
to break from?

If so, you would then have a
   break 2;
to break completely out of the loops.

I don't know what ever became of the talk of a parameterized break, but
it sound
good to me.  Any comments?

 >
 > Consider the next simple problem: search in a two-dimensional array
the
 > first element that is zero.
 >
 > In C++ this would become something like:
 >
 >   double anarray[13][7];
 >   unsigned x,y;
 >   for (y=0;y<13;++y)
 >       for (x=0;x<7;++x)
 >           if(anarray[y][x]==0)
 >               goto zero_found;
 >   zero_found:
 >
[snip]
 >
 > So, I propose a solution to this problem. Why not giving names to
 > syntactical constructions, like loops? Those names then could be used
as
 > an argument to break or continue. The previous program example would
 > become something like:
 >
 >   double anarray[13][7];
 >   unsigned x,y;
 >   for named vertical (y=0;y<13;++y)
 >       for named horizontal (x=0;x<7;++x)
 >           if(anarray[y][x]==0)
 >               break vertical;
 >

--
Bret Pehrson        mailto:BretP@strata3d.com
*Please post all questions to newsgroup
*Please carbon-copy all responses to newsgroup
--
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: djm5@ohgua.oh.lucent.com (Doug Murphy)
Date: 1997/03/13
Raw View
In article <33265E41.7A82@rug.ac.be>,
Vik Heyndrickx  <Vik.Heyndrickx@rug.ac.be> wrote:

>Consider the next simple problem: search in a two-dimensional array the
>first element that is
>zero.
>
>In C++ this would become something like:
>
>  double anarray[13][7];
>  unsigned x,y;
>  for (y=0;y<13;++y)
>      for (x=0;x<7;++x)
>          if(anarray[y][x]==0)
>              goto zero_found;
>  zero_found:
>
>Programmers that are rigorously against the use of goto will rewrite
>this by making use of a boolean variable.

    Or like this:

double anarray[13][7];
unsigned x,y;
for (y=0,x=0; x<7&&y<13; x<7?++x:(x=0,++y))
    if(anarray[y][x]==0)
        break;

    Voila!  No goto, no label, no labelled loops, no nothing!

Doug Murphy -- douglasmurphy@bell-labs.com
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: dacut@henry.ece.cmu.edu (David A. Cuthbert)
Date: 1997/03/13
Raw View
Jan Bielawski <jpb@msi.com> wrote:
>I'm probably missing something but what's wrong with:
>
> double anarray[13][7];
> unsigned x,y;
> for (y=0;y<13;++y) {
>     for (x=0;x<7;++x)
>  if(anarray[y][x]==0)
>      break;
>     if (x<7)
>  break;
> }

It's an extra comparison.  Comparisons are pretty inexpensive by
themselves, but here you've potentially added 13 of them.  If the
upper limit on y is in the millions, the run-time penalty could
be noticeable.

Of course, this is an optimization issue.  The best solution, IMHO,
is to use your method and, if a profiler shows a signficiant amount
of time being spent in this loop, then comment it out (with an
explanation as to why) and put the goto in there.
--
David A. Cuthbert
Graduate Student, Electrical and Computer Engineering
Data Storage Systems Center, Carnegie Mellon University
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: "Micha S. Berger" <aishdas@IDT.NET>
Date: 1997/03/14
Raw View
Doug Murphy <djm5@ohgua.oh.lucent.com> wrote:
: double anarray[13][7];
: unsigned x,y;
: for (y=0,x=0; x<7&&y<13; x<7?++x:(x=0,++y))
:     if(anarray[y][x]==0)
:         break;

:     Voila!  No goto, no label, no labelled loops, no nothing!

No legibility, either. If we didn't need an easy-to-maintain solution,
goto would have been fine.

--
Micha Berger 201 916-0287        Help free Ron Arad, held by Syria 3740 days!
micha@aishdas.org                         (16-Oct-86 - 13-Mar-97)
For a mitzvah is a candle, and the Torah its light.
http://aishdas.org -- Orthodox Judaism: Torah, Avodah, Chessed
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: damian@molly.cs.monash.edu.au (Damian Conway)
Date: 1997/03/14
Raw View
Vik Heyndrickx wrote:

> Why not giving names to
> syntactical constructions, like loops? Those names then could be used as
> an argument to break or continue. The previous program example would
> become something like:
>
>   double anarray[13][7];
>   unsigned x,y;
>   for named vertical (y=0;y<13;++y)
>       for named horizontal (x=0;x<7;++x)
>           if(anarray[y][x]==0)
>               break vertical;


Putting aside the religious debate over whether it's a desirable feature,
you can already do (almost) exactly this in (proto-)standard C++:

    #define  named(loopname)  goto loopname; loopname##_break: if (0) loopname:
    #define  break(loopname)  goto loopname##_break;


    double anarray[13][7];
    unsigned x,y;

    named (vertical) for (y=0;y<13;++y)
        named (horizontal) for (x=0;x<7;++x)
            if(anarray[y][x]==0)
                break (vertical);


You can still use ordinary (unnamed) breaks and you can "break" out of if's:

    named(outer) for (int i=1;i<10;i++)
    {
        named (oddif) if (i%2)
        {
            for (int j=1;j<10;j++)
            {
                cout << i << "," << j << endl;
                if (i==1) break;  // BREAK FROM INNER LOOP
                if (i==3) break (oddif); // BREAK FROM if (i%2) {...}
                if (i==5) break (outer); // BREAK FROM OUTER LOOP
            }
        }
    }


The only constraint is that "named" names and goto labels must all be
unique in their translation unit.

damian
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  who: Damian Conway                 email: damian@cs.monash.edu.au
where: Computer Science Dept.          web: http://www.cs.monash.edu.au/~damian
       Monash University             phone: +61-3-9905-5184
       Clayton 3168                    fax: +61-3-9905-5146
       AUSTRALIA                     quote: "A pessimist is never disappointed."
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: James Kanze <james-albert.kanze@vx.cit.alcatel.fr>
Date: 1997/03/14
Raw View
jpb@msi.com (Jan Bielawski) writes:

|>  In article <3326A2C9.653E@rug.ac.be> Vik Heyndrickx
|>  <Vik.Heyndrickx@rug.ac.be> writes:
|>  < Consider the next simple problem: search in a two-dimensional array the
|>  < first element that is zero.
|>  <
|>  < In C++ this would become something like:
|>  <
|>  <   double anarray[13][7];
|>  <   unsigned x,y;
|>  <   for (y=0;y<13;++y)
|>  <       for (x=0;x<7;++x)
|>  <           if(anarray[y][x]==0)
|>  <               goto zero_found;
|>  <   zero_found:
|>  <
|>  < Programmers that are rigorously against the use of goto will rewrite
|>  < this by making use of a boolean variable. Most of these people would
|>  < accept the use of break although this is a disguised goto, but one where
|>  < the destination is well known, namely the instruction after the loop.
|>  < Therefore it is acceptable in structured program. However in the case of
|>  < a nested loop this is not possible because the break would only
|>  < terminate the innermost loop.
|>
|>  I'm probably missing something but what's wrong with:
|>
|>   double anarray[13][7];
|>   unsigned x,y;
|>   for (y=0;y<13;++y) {
|>       for (x=0;x<7;++x)
|>    if(anarray[y][x]==0)
|>        break;
|>       if (x<7)
|>    break;
|>   }

For that matter, what's wrong with:

    double anArray[ 13 ][ 7 ] ;

    bool                found( false ) ;
    for ( int y = 0 ; ! found && y < 13 ; ++ y )
    {
     for ( int x = 0 ; ! found && x < 7 ; ++ x )
         found = anArray[ y ][ x ] == 0 ;
    }

Or (if you need to know more than just the point exists):

    double anArray[ 13 ][ 7 ] ;

    Fallible< pair< int , int > >
               firstZeroEntry ;
    for ( int y = 0 ; ! firstZeroEntry.isValid() && y < 13 ; ++ y )
    {
     for ( int x = 0 ; ! firstZeroEntry.isValid() && x < 7 ; ++ x )
         firstZeroEntry.validate( pair< int , int >( x , y ) ) ;
    }

--
James Kanze      home:     kanze@gabi-soft.fr        +33 (0)1 39 55 85 62
                 office:   kanze@vx.cit.alcatel.fr   +33 (0)1 69 63 14 54
GABI Software, Sarl., 22 rue Jacques-Lemercier, F-78000 Versailles France
     -- Conseils en informatique industrielle --
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: James Kanze <james-albert.kanze@vx.cit.alcatel.fr>
Date: 1997/03/14
Raw View
jpotter@falcon.lhup.edu (John E. Potter) writes:

|>  Semi-structured program.  In single-entry single-exit (structured)
|>  programming multiple extries and exits of loops and conditionals
|>  are rejected.  In semi-structured programming, this is relaxed to
|>  accept multiple exits from a loop.
|>
|>  for (;;) {
|>   ...
|>   if (someCondition)
|>    break;  // or goto a label at end of loop
|>   ...
|>   }
|>
|>  This is a structured program.

I don't think so.  Structured programming doesn't only require a single
exit, it requires that the exit be at the bottom.

Something like the above isn't too hard to follow in simple cases, but
when the break ends up in the middle of some deeply nested construct, it
can become confusing.

*Ideally*, the condition expressed in the second expression of the for
should be a loop invariant, true everywhere in the loop body.  In
practice, of course, the cure (of doing this) is sometimes worse that
the disease.

|>  There is a single exit from the loop.
|>  Structured has nothing to do with break/goto but how they are used.

Agreed.  I think that I could even argue that if the if with break is
the last statement in the for loop, it is be structured.  In this case,
however, why not just put the condition of the if in the condition of
the for, and make it obvious that it is structured.

|>  : However in the
|>  : case of a nested loop
|>  : this is not possible because the break would only terminate the
|>  : innermost loop.
|>
|>  Let me put on my purist hat and solve your problem.  Searches have
|>  empty bodies.  Any search with a non-empty body is messed up.
|>
|>   double anarray[13][7];
|>   unsigned x,y;
|>   for (y=0,x=0;y<13 && anarray[y][x] != 0;x==6?(x=0,++y):++x)
|>    ;

It's important to recognize that in fact, there are two searches
involved.  In fact, a functional programmer (or someone well versed in
STL?) would probably write it this way.  Someone from a procedural
background will probably use nested loops, which are the procedural
translation for tail recursive functions. (The two searches: you are
looking for a column which contains a zero, and to determine whether the
column contains a zero, you have a second search.)

Anyone care to post the STL solution.  It should involve a find_if whose
predicate is a function object doing a find.  I'm too lazy to work out
the details, though.

--
James Kanze      home:     kanze@gabi-soft.fr        +33 (0)1 39 55 85 62
                 office:   kanze@vx.cit.alcatel.fr   +33 (0)1 69 63 14 54
GABI Software, Sarl., 22 rue Jacques-Lemercier, F-78000 Versailles France
     -- Conseils en informatique industrielle --
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: James Kanze <james-albert.kanze@vx.cit.alcatel.fr>
Date: 1997/03/15
Raw View
djm5@ohgua.oh.lucent.com (Doug Murphy) writes:

|>  double anarray[13][7];
|>  unsigned x,y;
|>  for (y=0,x=0; x<7&&y<13; x<7?++x:(x=0,++y))
|>      if(anarray[y][x]==0)
|>          break;
|>
|>      Voila!  No goto, no label, no labelled loops, no nothing!

Including no readability.  There are two distinct linear searches
involved; your solution obfuscates this fact (which is fundamental to
understanding the code, and proving that it works).

--
James Kanze      home:     kanze@gabi-soft.fr        +33 (0)1 39 55 85 62
                 office:   kanze@vx.cit.alcatel.fr   +33 (0)1 69 63 14 54
GABI Software, Sarl., 22 rue Jacques-Lemercier, F-78000 Versailles France
     -- Conseils en informatique industrielle --
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Vik Heyndrickx <Vik.Heyndrickx@rug.ac.be>
Date: 1997/03/12
Raw View
Consider the next simple problem: search in a two-dimensional array the
first element that is
zero.

In C++ this would become something like:

  double anarray[13][7];
  unsigned x,y;
  for (y=0;y<13;++y)
      for (x=0;x<7;++x)
          if(anarray[y][x]==0)
              goto zero_found;
  zero_found:

Programmers that are rigorously against the use of goto will rewrite
this by making use of a
boolean variable. Most of these people would accept the use of break
although this is a
disguised goto, but one where the destination is well known, namely the
instruction after the
loop. Therefore it is acceptable in structured program. However in the
case of a nested loop
this is not possible because the break would only terminate the
innermost loop.

So, I propose a solution to this problem. Why not giving names to
syntactical constructions, like loops? Those names then could be used as
an argument to break or continue.
The previous program example would become something like:

  double anarray[13][7];
  unsigned x,y;
  for named vertical (y=0;y<13;++y)
      for named horizontal (x=0;x<7;++x)
          if(anarray[y][x]==0)
              break vertical;

The benefit may not be so clear in this example, however loops are
rarely this brief and in longer loops it is often difficult to overview
the entire loop.
Besides, an extra advantage would be the increased semantical value.
Also this could be more
generally implemented, i.e. not only for loop, but also do-while loop,
while-loops and even
switch statements.

Although, I've never programmed a compiler myself, I do not think this
would be difficult to
be accomplished. As this would be a superset of the current language
definition all existing
C++ (or C) programs would remain completely valid.

Any pros or cons, suggs?

Vik Heyndrickx, Wednesday, March 12, 1997
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: bparker@gil.com.au (Brian Parker)
Date: 1997/03/12
Raw View
Vik Heyndrickx <Vik.Heyndrickx@rug.ac.be> wrote:

>So, I propose a solution to this problem. Why not giving names to
>syntactical constructions, like loops? Those names then could be used as
>an argument to break or continue.
>The previous program example would become something like:

>  double anarray[13][7];
>  unsigned x,y;
>  for named vertical (y=0;y<13;++y)
>      for named horizontal (x=0;x<7;++x)
>          if(anarray[y][x]==0)
>              break vertical;

Java has a similar construct used pretty much as you describe (except
using labels instead of the keyword "named"). It does seem like a
useful extension, though of pretty minor significance in the greater
scheme of things, IMHO. (and of course you can always emulate it using
goto in a pinch).

,Brian Parker (bparker@gil.com.au)
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Vik Heyndrickx <Vik.Heyndrickx@rug.ac.be>
Date: 1997/03/12
Raw View
Consider the next simple problem: search in a two-dimensional array the
first element that is zero.

In C++ this would become something like:

  double anarray[13][7];
  unsigned x,y;
  for (y=0;y<13;++y)
      for (x=0;x<7;++x)
          if(anarray[y][x]==0)
              goto zero_found;
  zero_found:

Programmers that are rigorously against the use of goto will rewrite
this by making use of a boolean variable. Most of these people would
accept the use of break although this is a disguised goto, but one where
the destination is well known, namely the instruction after the loop.
Therefore it is acceptable in structured program. However in the case of
a nested loop this is not possible because the break would only
terminate the innermost loop.

So, I propose a solution to this problem. Why not giving names to
syntactical constructions, like loops? Those names then could be used as
an argument to break or continue. The previous program example would
become something like:

  double anarray[13][7];
  unsigned x,y;
  for named vertical (y=0;y<13;++y)
      for named horizontal (x=0;x<7;++x)
          if(anarray[y][x]==0)
              break vertical;

The benefit may not be so clear in this example, however loops are
rarely this brief and in longer loops it is often difficult to overview
the entire loop. Besides, an extra advantage would be the increased
semantical value.
Also this could be more generally implemented, i.e. not only for loop,
but also do-while loop, while-loops and even switch statements.

Although, I've never programmed a compiler myself, I do not think this
would be difficult to be accomplished. As this would be a superset of
the current language definition all existing C++ (or C) programs would
remain completely valid.

Any pros or cons, suggs?

Vik Heyndrickx, Wednesday, March 12, 1997
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: "Howard E. Hinant" <heh@beamtech.com>
Date: 1997/03/12
Raw View
Vik Heyndrickx wrote:

-snip-

> So, I propose a solution to this problem. Why not giving names to
> syntactical constructions, like loops? Those names then could be used as
> an argument to break or continue.
> The previous program example would become something like:
>
>   double anarray[13][7];
>   unsigned x,y;
>   for named vertical (y=0;y<13;++y)
>       for named horizontal (x=0;x<7;++x)
>           if(anarray[y][x]==0)
>               break vertical;
- snip -
>
> Any pros or cons, suggs?

Your suggestion is quite similar to the java solution:

   double anarray[13][7];
   unsigned x,y;
   for (y=0;y<13;++y)
       for (x=0;x<7;++x)
           if(anarray[y][x]==0)
               break vertical;
vertical:

In general I'm not a java fan, but they did get a few things right, and
this is one of them.  This is of course a goto, and people could abuse
it to the point of spaghetti code.  But hey, I can write bad code
without the help of gotos.  Anything can be abused.  You've got my vote
(not that that buys you much), but I slightly favor the java syntax
because of the increased flexibility.

-Howard
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Jason Merrill <jason@cygnus.com>
Date: 1997/03/12
Raw View
>>>>> Vik Heyndrickx <Vik.Heyndrickx@rug.ac.be> writes:

>   double anarray[13][7];
>   unsigned x,y;
>   for (y=0;y<13;++y)
>       for (x=0;x<7;++x)
>           if(anarray[y][x]==0)
>               goto zero_found;
>   zero_found:

> Programmers that are rigorously against the use of goto will rewrite this
> by making use of a boolean variable.  Most of these people would accept
> the use of break although this is a disguised goto, but one where the
> destination is well known, namely the instruction after the
> loop. Therefore it is acceptable in structured program.

Such programmers must get over themselves.  This is a perfectly reasonable
use of goto.  The destination is well known, because you can see the label
on the *next line*.  Perhaps they would be happier with a

  #define named_break goto

so they wouldn't have to see the hated word in their code?

In any case, it is far too late to be adding syntax to C++.

Jason
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: "Micha S. Berger" <aishdas@IDT.NET>
Date: 1997/03/12
Raw View
Brian Parker <bparker@gil.com.au> wrote:
: Java has a similar construct used pretty much as you describe (except
: using labels instead of the keyword "named"). It does seem like a
: useful extension, though of pretty minor significance in the greater
: scheme of things, IMHO. (and of course you can always emulate it using
: goto in a pinch).

Perl has named blocks as well, VERY useful for breaking out of nested
for loops.

Another bit it has is "redo", which is similar to continue but takes
you right after the increment (in a for() loop) and check.

Redo I can live without. But I miss named blocks. Just today I wrote
a pretty circumlocuted thing of break, do, and normal while that would
have been much more legible the other way.

-mi

--
Micha Berger 201 916-0287        Help free Ron Arad, held by Syria 3739 days!
micha@aishdas.org                         (16-Oct-86 - 12-Mar-97)
For a mitzvah is a candle, and the Torah its light.
http://aishdas.org -- Orthodox Judaism: Torah, Avodah, Chessed
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: lionelb@asi.fr (Lionel Bonnetier)
Date: 1997/03/12
Raw View
In article <3326A2C9.653E@rug.ac.be>, Vik Heyndrickx
<Vik.Heyndrickx@rug.ac.be> says...

>So, I propose a solution to this problem. Why not giving names to
>syntactical constructions, like loops? Those names then could be used as
>an argument to break or continue. The previous program example would
>become something like:
>
>  double anarray[13][7];
>  unsigned x,y;
>  for named vertical (y=0;y<13;++y)
>      for named horizontal (x=0;x<7;++x)
>          if(anarray[y][x]==0)
>              break vertical;

(snip)
>Also this could be more generally implemented, i.e. not only for loop,
>but also do-while loop, while-loops and even switch statements.


For human eyes such a break looks like a "return from ThisRoutine".

(For a compiler's eyes not at all, of course, since jumps and returns are very
different.)

Interesting how macros, routines, blocks, tend to become kinds of semantic
phrases... One day the compilers - if still here - will understand our jokes!


* Lionel Bonnetier * lionelb@asi.fr * Tel: 33 / (0) 478 601 862 *
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: thegoat4@airmail.net (Bryant Brandon)
Date: 1997/03/13
Raw View
In article <33265E41.7A82@rug.ac.be>, Vik Heyndrickx
<Vik.Heyndrickx@rug.ac.be> wrote:

>Consider the next simple problem: search in a two-dimensional array the
>first element that is
>zero.
>
>In C++ this would become something like:
>
>  double anarray[13][7];
>  unsigned x,y;
>  for (y=0;y<13;++y)
>      for (x=0;x<7;++x)
>          if(anarray[y][x]==0)
>              goto zero_found;
>  zero_found:
>
>Programmers that are rigorously against the use of goto will rewrite
>this by making use of a
>boolean variable. Most of these people would accept the use of break
>although this is a
>disguised goto, but one where the destination is well known, namely the
>instruction after the
>loop. Therefore it is acceptable in structured program. However in the
>case of a nested loop
>this is not possible because the break would only terminate the
>innermost loop.
>
>So, I propose a solution to this problem. Why not giving names to
>syntactical constructions, like loops? Those names then could be used as
>an argument to break or continue.
>The previous program example would become something like:
>
>  double anarray[13][7];
>  unsigned x,y;
>  for named vertical (y=0;y<13;++y)
>      for named horizontal (x=0;x<7;++x)
>          if(anarray[y][x]==0)
>              break vertical;
>
>The benefit may not be so clear in this example, however loops are
>rarely this brief and in longer loops it is often difficult to overview
>the entire loop.
>Besides, an extra advantage would be the increased semantical value.
>Also this could be more
>generally implemented, i.e. not only for loop, but also do-while loop,
>while-loops and even
>switch statements.
>
>Although, I've never programmed a compiler myself, I do not think this
>would be difficult to
>be accomplished. As this would be a superset of the current language
>definition all existing
>C++ (or C) programs would remain completely valid.
>
>Any pros or cons, suggs?
>
>Vik Heyndrickx, Wednesday, March 12, 1997

   Here's what I do:

    double anarray[13][7];
    unsigned x,y;
    for (y=0;y<13;++y) {
        for (x=0;x<7;++x) {
            if(anarray[y][x]==0)
                goto vertical;
         } horizontal:;
    } vertical:;

   It still uses 'goto', but it's pretty clear what happens.

B.B.
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: jpb@msi.com (Jan Bielawski)
Date: 1997/03/13
Raw View
In article <3326A2C9.653E@rug.ac.be> Vik Heyndrickx
<Vik.Heyndrickx@rug.ac.be> writes:
< Consider the next simple problem: search in a two-dimensional array the
< first element that is zero.
<
< In C++ this would become something like:
<
<   double anarray[13][7];
<   unsigned x,y;
<   for (y=0;y<13;++y)
<       for (x=0;x<7;++x)
<           if(anarray[y][x]==0)
<               goto zero_found;
<   zero_found:
<
< Programmers that are rigorously against the use of goto will rewrite
< this by making use of a boolean variable. Most of these people would
< accept the use of break although this is a disguised goto, but one where
< the destination is well known, namely the instruction after the loop.
< Therefore it is acceptable in structured program. However in the case of
< a nested loop this is not possible because the break would only
< terminate the innermost loop.

I'm probably missing something but what's wrong with:

 double anarray[13][7];
 unsigned x,y;
 for (y=0;y<13;++y) {
     for (x=0;x<7;++x)
  if(anarray[y][x]==0)
      break;
     if (x<7)
  break;
 }
--
Jan Bielawski
Molecular Simulations, Inc.    )\._.,--....,'``.
San Diego, CA                 /,   _.. \   _\  ;`._ ,.
jpb@msi.com               fL `._.-(,_..'--(,_..'`-.;.'
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]