GOTO, why are you adverse to using it

Started by
74 comments, last by SmkViper 9 years, 7 months ago

I am an old school programmer, did many stints in assembly (6502,6510,68000,68030,486,586), basic, fortran, pascal, extended languages, c++, c# etc... I use goto on a regular basis to exit out of routines, skipping many lines of code and only incurring a single cache hit. In over 30+ years I know when the proper use of the command is needed, it's no worse than BREAK or CONTINUE for a loop, actually less in fact. What is your aversion to using that command, is it your workplace or your training? I can skip a thousand lines of code with a single command and a single cache hit. Do you have to jump through hoops to get out of a routine? With my experience I know when to use it and not to use it. I want to hear from the professionals why it's such a bad command to use. My typical use is goto ex; which is jump to the exit routine, everything is done, clean up and get out. I'm not a pro by any means (mid-south US, no programming jobs here), just wondering about all the hate on goto is about, it's a very useful command...

******************************************************************************************
Youtube Channel

Advertisement

IIRC, "goto considered harmful" was authored in the 60's, and made the argument on the comparison between structured and unstructured programming.

At the asm level, everything is a goto, so they're obviously not the devil. The argument is that certain uses have a structure -- if/then/else, for/break/do/while, switch, call -- and that this structure makes programs easier to reason about. Without any structure, programs are just spaghetti.

This is obvious at the time, but it was something that actually had to be explained back then -- structured flow control is better than spaghetti. High level flow control patterns are a good thing.

Goto usually isn't required in high-level programming because we've formalized all the useful uses of it into flow control keywords already.

The main remaining use of it in C is to implement error handling with cleanup -- e.g. when there's multiple exit points in a funciton, but they all need to perform the same series of cleanup tasks to avoid resource leaks.

In newer languages, this pattern is available by the use of RAII/destructors/stack-unwinding/finally, so goto isn't required for that particular structure any more either.

I have no aversion. The way I write code means a goto is never necessary. I've never ran into a problem and thought to myself that a goto would be cleanest solution in C#, Javascript or C++. Maybe it's useful outside of those languages. I remember seeing it used in C and that's it. I use lambdas a lot and lambda callbacks rather than returns. It's very flexible especially with asynchronous stuff.

This argument just came up on the ISOCPP mailing lists a few weeks ago, actually. The specifics were arguments for multi-level break but comparisons to goto came up of course.

Ultimately, the problem is reasoning about the structure of code. I need to read and maintain code far, far, far more often than I give any remote concern to using "a single command and a single cache hit," even in performance-sensitive domains like gaming. Gotos make it hard to tell not only where code flow might go but how the code flow can reach a particular point.

This is also why some of us despise exceptions with a complete and utter passion.

Sean Middleditch – Game Systems Engineer – Join my team!

When I first learned to program is was with basic and GOTO was all we had. I understand they can have their uses, but along with line #'s I'm quite glad to see them generally regulated to the annuls of history. But unlike Sean, I LOVE exceptions. I guess to each is own ;)

I do rarely use goto, in C++ and even C#.

This is if I have a few nested loops and on occasion need to restart the whole shebang or for multi level break. I try to keep the target on the same screen as the goto call though.

Yes, some academics would then explode that code into 5 sub functions and thus shred related code to pieces. This does NOT increase readability IMHO.

Also, I despise exceptions. They make people lazy (I have a problem, let's pass it to someone else). In some cases they help have "cleaner" code. Until you really try to have exception clean code. On the top level you would have to try/catch every single line by itself, unless you can assure there are NO side effects if one of the sub steps fails.

Fruny: Ftagn! Ia! Ia! std::time_put_byname! Mglui naflftagn std::codecvt eY'ha-nthlei!,char,mbstate_t>

The primary reason I'm averse to using goto is because I know that a sizeable proportion of my colleagues are averse to seeing goto. It's pretty rare that I miss it though.

Oh, I use goto on a regular basis. I've used it twice in the last 10 years, which means I write about one goto statement every fifth year. I'm not adverse, but imho goto is lame, real programmers use comefrom.

openwar - the real-time tactical war-game platform

Saying GOTO is harmful is like saying chopsticks are harmful. GOTO is a tool which is good for some things and not so good for others. Saying "GOTO can't be used ever for anything because it's bad, m'kay?" is silly.

Personally, I often prefer to use GOTO liberally while writing driver and other low level code in C. Here, I regularly write functions consisting of longish sequences of steps involving HW states and kernel resources. Each of these steps need to succeed and the only "else" action for any of the individual steps failing is to roll back everything done so far much more carefully than what I could get away with in "application/user mode code". Due to being limited to C, I can't rely on RAII, destructors, exceptions and stuff like that to clean up after me when something goes wrong.

Why not if-else or nested functions? A 25 step function would lead to 25 nested if-else statements or 25 nested function calls. I consider this worse from maintainability and "code esthetic" points of view than repeating 25 times "do something; if (failed) goto RECOVER;" with a roll-back section at the end of the function.

That said, I practically never use GOTO in/with higher level code/languages (C++, C#, Java, etc.) where I rely on the in-voque mechanisms of garbage collection, RAII, exceptions (and, like most user mode code developers, perhaps unconsciously, eventually the OS cleaning up my mess after my process crashes).

When I had a Pascal course back in 1991, the teacher we had enforced strict prohibition to gotos, arguing that you should be able to draw a flow chart from top to bottom with no crossing line of flow. Goto obviously breaks this. I never used goto since then, and I actually never had any need to use goto either, but I do break the flow according to flow charts every day:

Break and continue breaks the flow, so does early exits with return, so as far as I am concerned, if goto is considered evil, so is break, continue and premature returns too.

Edit:

Multi level break is a problem of course. I think Swift has solved that by labelling the loops so you could name the loop you wanted to break, ie. 'break columnLoop', for instance.

This topic is closed to new replies.

Advertisement