Fog Creek Software
Discussion Board




How bad is goto, really?

Has anyone worked with gotos frequently and found that they're particuarly scary in the hands of bad programmers?

That paper "Goto considered harmful" was actually changed from "A case against the goto statement", and the author bitterly reflected that people just cite its name without actually reading the paper. I wonder if we're understandably scared about other peoples' code and sometimes just prop up any scapegoat.

It would be best for readers if you have dealt with goto code from multiple people at different companies. If that means no one replies, well that's better than shaky info. ;)

Tayssir John Gabbour
Friday, August 20, 2004

I don't miss it in Java, since automatic memory management and the finally command make goto's unnecessary. I used goto a little in C, mainly to jump to the end of a function to free memory.

In practice, goto overuse seems rare, since most people have learned that it's harmful. This assume that you aren't a purist who classifies exceptions as gotos.

Julian
Friday, August 20, 2004

It's not that bad. Look at generated assembly language. It's full of GOTOs.

But nowadays in high level languages there are usually alternate control structures that are more appropriate.

passive-aggressive weasel
Friday, August 20, 2004

I have seen a few gotos, and used a few.  Mostly for rollback or reset code.

In every occasion I could see that extra states in a state machine, or exceptions, or even duplicating large chunks of cleanup code, or nested functions, could have done the same trick; but generally, I don't think in the exact situations that I have encountered gotos, that those alternatives would have made code clearer!  There is nothing ambiguous about "goto abort;".  In fact, my text editor puts useful arrows matching gotos and labels, amoung other things.

(Although throwing 'new' exceptions takes memory which is not always a good solution when responding to an out-of-memory situation on a constrained device such as a mobile phone.)

i like i
Friday, August 20, 2004

Gotos are all over the place
break
Exit Do
continue

Lots of control structures in lots of languages have  implied gotos. Function calls are themselves just abstractions of goto. They work because we can tell where they jump. The goto statement itself can be just as graceful. Just because some people misuse it doesn't make it evil. It's a tool like everything else.

Troy King
Friday, August 20, 2004

"Gotos are all over the place
break
Exit Do
continue"

But these are "gotos" from a specific context to a specific place in the code and not from one arbitrary location in code to some label that may be at any other arbitrary location.
This characteristic is the "evil" part in Dijkstra's essay because it compromises the "coordinate system" he uses to describe the state of the code during runtime.
Because of the specific context and target of these special cases, this "coordinate system" remains intact.

Geert-Jan Thomas
Friday, August 20, 2004

Other than error handling in VB, the only time that I've seen horrendous use of goto's was in a C programming book for a class I took back in 1988.

The book had huge code samples littered with goto's.  The other thing I remember is that all the boolean variables were named flag (flag1, flag2, ..., flag50).

The book was incomprehensible. I remember taking a red pen and drawing arrows all over the place to show the jumps.  Red spaghetti.

Yet another anon
Friday, August 20, 2004

...I can tell you the temptation to mususe these things is awful.

Calvin
Friday, August 20, 2004

>Gotos are all over the place
>break
>Exit Do
>continue

In over ten years of software development I've never used one of them.


Friday, August 20, 2004

I've seen goto in a fair amount of "C++" (C++ written by C programmers) code. In a tiny minority of cases it has been a clean and efficent solution to a problem, in the rest it's a minor form of code obscuration.

Not evil, but defininetly a tad mischevious.

Mr Jack
Friday, August 20, 2004

I don't see the temptation for misuse -- it looks ugly and breaks the flow.

It's useful when breaking out of a nested loop, where structured programming would require a boolean or something.

Alex
Friday, August 20, 2004

I once worked in finance on big mainframe systems running coboll.  Company policy was that goto was good - but with lots of stringent conditions.  One rule was that certain cobol loop constructs should not be used (variants of the keyword 'perform') and that goto should be used in place.  This was the only allowable instance that a goto should move 'up' the code and another rule said that any other goto was fine as long as it always moved 'down'. 

Now since best practice in cobol was not to use goto and to use the above mentioned 'perform' keyword, I had lots of problems in the first few weeks getting used to it.  However, I eventually noticed that since everyone expected goto to be used they were all attuned to thinking in terms of goto and consequently no one ever wrote spectacularly bad code that employed it.

While I wouldn't advocate using it (takes a while to get yourself into the mindset) I can say that I have seen it used in real life with no (apparent) ill effect - apart from the general mental trauma of working in cobol: :-)

anonymouse
Friday, August 20, 2004

There's a good discussion in Code Complete (either edition)

Dave Hallett
Friday, August 20, 2004

If break is a form of goto, then I use it. I could avoid it easily but it enables me to easily have only one exit point in my functions. I prefer (in a language I just made up)...

function foobar() {
    retvalue = null;

    if (a == b) {
        if (c == null)
            break;
        // do some other stuff here
    }

    return retvalue;
}

to

function foobar() {
    retvalue = null;

    if (a == b) {
        if (c == null)
            return null;
        // do some other stuff here
    }

    return retvalue;
}

Herr Herr
Friday, August 20, 2004

Or without a break

function foobar() {
    retvalue = null;

    if (a == b) {
        if (c != null)
        {
            // do some other stuff here
        }
    }

    return retvalue;
}

Simple, really.


Friday, August 20, 2004

Things like break aren't what I'm looking for, since those are more special purpose syntactic sugar. It's sugar I definitely agree with, but a different subject.

Tayssir John Gabbour
Friday, August 20, 2004

Its very common and useful in C for cleanup of routines. The following demonstates the idiom (I hope the spaces show properly):

void Foo()
{
BAR* x = NULL;
BAR* Y = NULL;

x = AlllocBar();
if (x == NULL) {
  goto done;
}

y = AlllocBar();
if (y == NULL) {
  goto done;
}

...


done:
if(x)
  FreeBar(x);
if(y)
  FreeBar(Y);
}


This is about the only use for it I would advocate.

ronk!
Friday, August 20, 2004

The only appropriate use of GOTO that I've seen is in C code to act in a manner similar to the Finally of a try/catch block. You've got

int foo()
{
/* bleah bleah bleah */

tidyup:
    /* release resources etc */
}

If the body of the function has multiple exit paths, you don't want to repeat the tidyup code too much, so jump to it and leave. In some cases I've seen this can make the code significantly more elegant, and at least tidies the code up.

In this context it can be useful and isn't altogether harmful. The possible abuses of this construct, as with all other uses of goto, is very high, though.

.
Friday, August 20, 2004

Aw, poo. Either too much coffee or not enough. I'll pay attention next time.

.
Friday, August 20, 2004

void TextBookExample_Transaction() {
  if(!do_step1()) goto rollback1;
  if(!do_step2()) goto rollback2;
  if(!do_step3()) goto rollback3;
commit:
  return;
rollback3:
  undo_step2();
rollback2:
  undo_step1();
rollback1:
}

i like i
Friday, August 20, 2004

I have said my opinion here before that goto is not always harmful. Don Knuth wrote a paper titled "Structured Programming Using Goto Statements" where he stressed that many times avoiding goto will make the code less modular than with the goto. I haven't read it, but it seems to make sense.

One of my most ugly abuses of goto was when I was trying to write a parser for a subset of the Bourne Shell syntax. Fixing a couple of bug made me add many labels, and quite a lot of goto statements. Maybe there's a way to refactor it to make it more structured, but since the code does its job and I don't have to further modify it, I'm keeping it as it is.

You can find the code here:

http://tinyurl.com/5mn5y

Shlomi Fish
Friday, August 20, 2004

Your text book example rollback might be OK in C, but it's a shoddy way of writing it in C++ where RAII offers a far better method.

Mr Jack
Friday, August 20, 2004

My preferred use of break-

int foobar() {
int result = 0;

if ( true ) {
  if ( a != b ) break;
      c = f( a, b )
  if ( 0 != c ) break;
      result = g( c )
}
return result;
}

Breaker 1 9
Friday, August 20, 2004

The immediate, automatic backlash against goto from the insecure propellerheads among us is fiery; a sort of "terminate with extreme prejudice" instinct.  I've certainly been in meetings where my fellow developers have been cajoled and openly ridiculed for using goto, even in sensible contexts.

So to answer the original question:  from a technical perspective, I think goto is fine in limited circumstances.  This has been discussed to death.

But using goto may tag you as inexperienced, stupid, unworthy, and beneath the haughty assholes who dogmatically oppose it.

Be careful. :)

indeed
Friday, August 20, 2004

I done a lot of assembly language programming ... and I find structured programming constructs (for, while, etc) more readable and more writeable ... so much so that I prefer to use structured programming in C/C++, even though C/C++ supports "if (...) goto ...;" statements if I wanted them.

Christopher Wells
Friday, August 20, 2004

If you have never written code in FORTRAN, you don't know the ubiquity that goto statements had. Nor the difficulty in trying to debug such code.

http://www.engr.umd.edu/~nsw/ench250/fortran1.htm

Statements like:
goto (100,200,300,400,500), i

which means, if i <= 1 then goto 100, if i =2 then goto 200, and so on, if i >=5 then goto 500.

are used in modern languages like:
select case i
or switch(i)

Then there is one of the types of IF statements where you go to a different place depending on whether the result is negative, zero or positive.

IF ( VAR ) 100,200,300

And then there were some odd thing called an assigned goto, which was really wierd.

In short, writing structured FORTRAN was very hard. Writing spaghetti code was far easier. It is very hard to maintain spaghetti code. Too many GOTOs in your code turned it into write-only code (no one could figure out what it did, so no one could debug nor maintain it).

A dumb question to ask in an interview is "when would you use a goto statement?" I have found no reason to use them since using any programming language more modern than FORTRAN. I am sure you can think of one. I, personally, have never come across a case where a goto was a better choice than some other control structure.

Peter
Friday, August 20, 2004

One could argue that a return statement anywhere except prior to a function's close '}' is a form of goto.

There are some good programming practices, which are specifically found in Scott Meyers' "Effective C++" books.

And I like the way he phrases things too, using the word "prefer" over "must" or always.

For example, I prefer loops to be in the for() (as opposed to while or do) syntax, with all iterators and conditionals being handled within the for()  construct.  But while the attempt is to up front and clear about the loop parameters, it can sometimes lead to confusion as well. So when it does not improve code readability, don't use it.

Same with goto.  How hard is that?

hoser
Friday, August 20, 2004

Someone posted like 4 if conditions with goto...but what happened to using switch ?

Jon
Friday, August 20, 2004

hoser: as was pointed out earlier, breaks, continues, and the situation you cite are not true gotos, which can jump from anywhere to anywhere. The case of break, continue, and return, the language defines precisely where control transfers to, and the programmer has no control over that when using the statement.

Dijkstra's paper is a must-read, along with early Parnas, Knuth, etc. I wish universities had a course that consisted of required reading in the classics...

Jeff Kotula
Friday, August 20, 2004

I just realized my last post sounded kind of snotty. Sorry 'bout that -- didn't mean it that way...

Jeff Kotula
Friday, August 20, 2004

The only useful place I've ever used goto was in eliminating tail recursion. It was an exercise in one of my programming classes and I had to use it in an application that drew a model for a statistical processing package I did some work on. The validation routine checked for cycles in the graph, since these were illegal, and for the first (and last) time I found the use of goto and multiple stacks easier than using recursion or any other control structures.

Goto has its uses. The collective wisdom here seems to be that goto should be used sparingly, which makes more sense to me than the more common place repulsive response to the construct. I've seen people that have the same reflexive repulsed response to recursion as most people seem to have with 'goto'. Both mystify me, because in the proper context both constructs can be very useful.

Mike
Friday, August 20, 2004

Your as bad as you want to be baby!

sorry.

Doug Withau
Friday, August 20, 2004

I worked at a place where the Vice President of Engineering made all the rules and was responsible for personally coding the trickiest parts of the applications. He had a PhD in Sociology - he bragged that he learned BASIC all by himself. He had never studied CS.

sample code:

#define LET
...
LET x=1;
LOOP_17:
Z = Z + strlen(CONSTANT_SIZE_STRING);
if (X <= 10) goto LOOP_17;

Dennis Atkins
Saturday, August 21, 2004

I should mention that at the time I made $5/hr and he made $750,000/yr.

Dennis Atkins
Saturday, August 21, 2004

"If you have never written code in FORTRAN, you don't know the ubiquity that goto statements had."

Good point. Languages that aren't well-developed can encourage overuse of a powerful construct. And that can stigmatize the powerful construct because it was more a symptom than a disease.

I did a little Fortran 77 to extend a physics dept's legacy software. I wish I could remember the control structures I used.

Tayssir John Gabbour
Saturday, August 21, 2004

void TextBookExample_Transaction() {
  if(do_step1())  {
  if(do_step2())  {
    if(do_step3()) return;
    else undo_step2();
  };
  else undo_step1();
  }
}

Basic structured programming, nothing like your spaghetti with three "goto"s.

(Disclaimer: the above is only to illustrate how it is done in a structured form; I make no claims about it being correct or free from bugs - I only spent two minutes on it.)

.
Saturday, August 21, 2004

"I did a little Fortran 77 to extend a physics dept's legacy software. I wish I could remember the control structures I used."

Computed GOTOs? Procedures with multiple ENTRY points? :-D

Chris Nahr
Saturday, August 21, 2004

... oops, there is a bug. :) There's a situation when one undo is not reached.

.
Sunday, August 22, 2004

I just recently used goto in an ASP.NET web application written in C#. Basically, a login is attempted. If the login is unsuccessful and a specific error is given, then the system tries to enroll the user. If that is successful, then it has to sign them on. Using a single goto, I avoid repeating myself with the sign on validation. Control is passed back up to right before the results of the login attempt are validated.

I wrestled with trying to avoid using the goto because of the stigma, but there wasn't any way to get around it without massive circumlocutions. Goto is best used sparingly; I don't think there's any reason to avoid using it entirely.

Bill Brown
Sunday, August 22, 2004

Since my experience is mostly with Fortran, I shall restrict my comment to the use of goto's within that language.

First, please recall that even the renowned Prof. Donald Knuth cites how proper use of goto's can theoretically lead to structured programming:  "Structured Programming with go to Statements", Computing Surveys, Vol. 6, No. 4 (December 1974), 261-301.  In particular, please see pages 289-290.

In reality, however, goto's generally end up being misused, with the result that such Fortran code is difficult to either maintain or to enhance.

For consideration of the curious amongst readers of this forum, we at COMP-AID have come up with a way for taming or controlling the use of goto's in Fortran code, thereby permitting us to refactor old, legacy, difficult-to-understand Fortran code.  Amazingly, it is quite a simple concept. 

At any rate, if you're curious, there is an 18 page brochure explaining this methodology on the DOWNLOAD page of our web site at
      www.TheComp-AidCompany.com
No e-mail address is requested, so you can be totally anonymous in downloading this brochure in PDF format.

Best regards,
Ron Wackwitz

Ronald C. Wackwitz
Monday, August 30, 2004

*  Recent Topics

*  Fog Creek Home