What is wrong with using goto? [duplicate]
Asked Answered
S

6

235

Possible Duplicates:
Why is it bad to use goto?
GOTO still considered harmful?

I was ramdomming through xkcd and saw this one (if also read some negative texts about them some years ago):
your slow connection sucks, get a faster one to see this image
What is actually wrong with it? Why are goto's even possible in C++ then?

Why should I not use them?

Semifinal answered 19/8, 2010 at 0:5 Comment(5)
This blog on the topic is worth a read: blog.smartbear.com/development/…Pedigo
The best reason to avoid GOTO is exemplified by the xkcd cartoon: if you use GOTO, you're likely to be attacked by a dinosaur.Succession
The answer with same graphic on another post.Formyl
Check out Dijkstra's original Go to statement considered harmful. But don't forget Knuth's Structured programming with goto statements which explains why you might use them and how they can fit with rather than oppose the goals of structured programmingBefitting
It is wrong to use GOTO, if one can achieve the same thing with an IF...ELSE... statement, a FOR or a DO ... WHILE loop, an automatically destructed RAII object or any other high level construct. There are cases, though, where a single well placed GOTO eliminates duplicate code and/or a temporary boolean, without making the code unclear or ureadable. And in those cases, it SHOULD be used.Superscription
B
177

Because they lead to spaghetti code.

In the past, programming languages didn't have while loops, if statements, etc., and programmers used goto to make up the logic of their programs. It lead to an unmaintainable mess.

That's why the CS gods created methods, conditionals and loops. Structured programming was a revolution at the time.

gotos are appropriate in a few places, such as for jumping out of nested loops.

Blurt answered 19/8, 2010 at 0:10 Comment(15)
Jumping out of nested loops are the only instance I have used goto statements. Even then, I refactor my code to simply return early when possible.Washerman
+1 for acknowledging that goto still has a purpose on rare occasions.Localism
I remember reading gotos are often used by some tools that auto-generate code, like parser generators etc.Hightower
I know this is an old post, but I thought I'd add one more use for goto. In SQR goto is commonly used as a 'continue' in a loop. Many database languages don't have continues in the language so they put a goto at the end of the loop and call it if they need to 'continue'.Attar
More accurate to say because they can easily lead to spaghetti code if not used wisely. Sometimes it is actually the cleanest, DRYest way of doing things, especially in languages that don't focus on structured programming, as I've just discovered when trying to make a loop continue in T-SQL.Pronate
A return can be used instead of goto to jump out of nested loops. For example, extract the nested loops into a new function and return from there when the condition that triggers the goto is satisfied. I only see goto being used only to get an extra bit of performanceHypocycloid
"In the past, programming languages didn't have .... if statements" err. Basic always had if statements... as did most assembly languages. (although "if" might be "jump if zero") As for using goto in nested loops; personally I'd argue that if you want to jump out a nested loop; then you make a function and return from it.Bridgeport
@Hypocycloid That create a new function thing often isn't a good solution when your current function has a bunch of context with it that you'd have to pass around. Also, what if you have nested loops and conditions and you don't want to jump all the way out? Once you go beyond basic code this sort of scenario definitely happens here and there and goto is a very clean, easy, readable solution.Sexy
@Sexy The important thing is that at the end the code should be as much understandable as possible, whether using a goto or not. The best solution will depend on a case basis, but I still have to see a goto proving to be the best understandable solution. Perhaps this is because I mostly use only functional programming.Hypocycloid
@Sexy Beware that a function with a bunch of context is perhaps doing to much, and a candidate to be broken into simpler functions, thus making the final code more understandable. Again, I suppose there will be exceptional cases ... but very frequently in C programs I see enormous functions that can scare anyone a lot. I wonder how many bugs are hidden there ;-)Hypocycloid
@Hypocycloid I gave you the instances in which goto is the best solution: nested loops and conditions. Try looping through multiple dimensions, or looping through a bunch of trees or linked lists simultaneously. Video game and graphing applications come to mind, where you have lots of structured data loading, graphics, stitching data together and apart, etc. In some situations, where you are exactly in an algorithm's "steps" can be several pieces of context in and of itself. Splitting your code up into many small functions is a bad idea, because then you're looping over many call stack operations.Sexy
@Sexy A good compiler would let it be instructed to inline the function calls as appropriate to avoid a negative performance impact inside nested loops, while retaining the greater understandability of having smaller focused functions. If you are in C++ you can throw an exception to do a non-local return from deep inside several nested function calls, and likewise, it can be done in C using setjmp and longjmp (see here). But for a typical few cases I admit that a goto may be the best option.Hypocycloid
@Hypocycloid That's true until you factor in the context you have to pass around and return in order to replace the goto functionality, and then it's not going to get optimized. Both of your other examples are slow, and exceptions are not made for this purpose.Sexy
JavaScript lets you break out of labelled loops, which I've found useful.Scanner
In many cases "spaghetti code" is result after desperate attempts to avoid use of goto! And BTW too many examples in MSDN (Win32 API) include goto. In Linux source you can find goto as well!Yclept
A
111

Nothing is wrong with goto if it is used properly. The reason it is "taboo" is because in the early days of C, programmers (often coming from an assembly background) would use goto to create incredibly hard-to-understand code.

Most of the time, you can live without goto and be fine. There are a few instances, however, where goto can be useful. The prime example is a case like:

for (i = 0; i < 1000; i++) {
    for (j = 0; j < 1000; j++) {
        for (k = 0; k < 1000; k++) {
            ...
            if (condition)
                goto break_out;
            ....
        }
    }
}
break_out:

Using a goto to jump out of a deeply-nested loop can often be cleaner than using a condition variable and checking it on every level.

Using goto to implement subroutines is the main way it is abused. This creates so-called "spaghetti code" that is unnecessarily difficult to read and maintain.

Antigua answered 19/8, 2010 at 0:14 Comment(10)
What if there are some automatic objects constructed on the stack, which are local inside the loop? Goto will jump to some other place, jumping over the end of the blocks, where the destructors for these objects are called. Right? In most cases, it won't do anything bad. But there are cases where it WILL do, including losing user's data etc.Detent
@SasQ: The compiler is responsible for ensuring that the actual "jmp" instruction generated for the goto is preceded by whatever code would be necessary to get rid of inner scope variables.Alica
It's not true that goto can jump between functions. C has longjmp() for that, and C++ has exceptions.Runnel
regarding your claim that "goto can also be used to jump from one function into another without making a function call": **your claim that you can use goto to "jump from one function into another without making a function call" is wrong as explained by here and here and also see the comment directly above by @celticminstrel.Steffen
@TrevorBoydSmith- You're right, I must have been thinking about longjmp (same problematic concept, different interface). Fixed.Antigua
If you need a O(N^3) loop, maybe goto is the least of your concerns.Spinode
@Spinode If you don't ever work with such loops, maybe goto is the least of your concerns.Sexy
@Sexy I try as much as I can, not to, and it's not so hard, I'm very doubtful that any company nowadays accepts a piece of code with over O(N^2), and even O(N^2) is a stretch.Spinode
@Spinode Plenty of companies would. There is a vast variety of different software out there, and many of them require complicated nesting.Sexy
The reason it is taboo predates C by several years. Dijkstra’s letter was published in 1968.Reider
H
49

There is nothing wrong with goto in itself. It's a very useful construct in programming and has many valid uses. The best that comes to mind is structured resource freeing in C programs.

Where goto goes wrong is when it is abused. Abuse of goto can lead to thoroughly unreadable and unmaintainable code.

Hitch answered 19/8, 2010 at 0:8 Comment(0)
J
35

In 1968, Edsger Dijkstra wrote a famous letter to the editor of Communications of the ACM GOTO is considered harmful in which he laid out the case for structured programming with while loops and if...then...else conditionals. When GOTO is used to substitute for these control structures, the result is very often spaghetti code. Pretty much every programming language in use to day is a structured programming language, and use of GOTOs has been pretty much eliminated. In fact, Java, Scala, Ruby, and Python don't have a goto command at all.

C, C++ and Perl still do have a GOTO command, and there are situations (in C particularly) where a GOTO is useful, for example a break statement that exits multiple loops, or as a way of concentrating cleanup code in a single place in a function even when there are multiple ways to terminate the function (e.g. by returning error codes at multiple points in the progress of a function). But generally its use should be restricted to specific design patterns that call for it in a controlled and recognized way.

(In C++, it's better to use RAII or a ScopeGuard (more) instead of using GOTO for cleanup. But GOTO is a frequently used idiom in the Linux kernel (another source) which is a great example of idiomatic C code.)

The XKCD comic is a joke on the question "Should GOTO always be considered harmful when there are certain specific design patterns that are helped greatly by its use?"

Janice answered 19/8, 2010 at 0:13 Comment(8)
And that GOTO's went out with the (computing) dinosaursBullate
@Gerry: that's a good one. I hadn't thought of that.Janice
Actually, with the goto he used (to goto a subroutine of some sort), raptors should attack him.Janice
I find that the DIjkstra explanation (and its direct consequences) is the true reason not to use goto, and not just the "unstructured code" everybody think it´s all about. There are more implications, and you are right to mention it.Oddment
Java don't have a goto command but a break who serve the same purposeVeinule
You guys should have used C64 Basic V2.0. released more than 10 years after the Dijkstra's paper, this language has neither else nor the loops, besides a for loop that you could misnest by accident. Bill Gates is personally responsible for this abomination, BTW.Polyzoarium
"Java don't have a goto command but a break who serve the same purpose" No. break is much more limited in scope. Break can only be used to exit the loop prematurely and to exit switch block, which seems to be like a C carryover.Jennette
Thank you, I was trying to explain to a coworker today why I use goto statements in my private/hobby object-oriented C graphics engine code. I use them inside of the constructors in order to jump out of memory allocation steps, call the destructor on the return object, and return NULL. This turned out to be far more readable than calling the destructor and returning NULL inside of each NULL check or creating expanding lists of free statements. I was somewhat cautious to the idea of using them but it just made sense there. I make sure to be consistent with it.Priscian
P
11

Did you google the issue?

The founder of the anti-goto movement is Edsger Dijskstra with his legendary "Goto Considered Harmful"

To get you started you can goto (ha ha!) http://en.wikipedia.org/wiki/GOTO

Prau answered 19/8, 2010 at 0:9 Comment(1)
Ironically, he actually tolerated far more GOTO than programmers today. For Djikstra, forward GOTO is okay, backward GOTO and GOTO into the inside of the loop is not.Jennette
M
10

It's possible in C++ because it's possible in C. Whether you should or shouldn't use it is long-standing religious war.

It was a design goal of C++ that 99-point-something percent of C programs in the wild should compile and run with the same functionality in C++. Including goto was part of the effort to reach that goal.

Microreader answered 19/8, 2010 at 0:8 Comment(8)
Apparently the author of the question is unaware why "goto" is available in C, too.Oneil
C++ is not a superset of C.Semifinal
It's not, but one of the original goals (and, apparently, banes) of C++ was strong compatibility with C. And I still don't get what you are so upset about.Microreader
@kon to be fair you have to write really ancient style C code to make it not valid in C++, mod russians back up :-)Shouse
Hey, thanks, I didn't know there was russian mob around here :)Microreader
I haven’t ever heard anyone argue that you should ever use goto in new C++ programs. Fortunately.Ferdinande
@Ole You should definitely use goto at times in new c++ code.Sexy
@Shouse There are some handy (and quite commonly used) features in C that are unfortunately not available in C++ (e.g. automatic void* casts and designated initializers)Nickolas

© 2022 - 2024 — McMap. All rights reserved.