> What you are saying is that there's nothing wrong with the efficiency of the goto statement.
I didn't specifically say that in my earlier post. But, yes, there's nothing wrong with the efficiency of the goto statement.
That compilers optimized flow control constructs better than jumps was probably true at some point in history; around the time that compilers would generate more efficient code if a program used a shift operation instead of a multiply. Current C++ compilers perform data flow analysis; it makes no difference to the optimiser whether a goto was used or a break or continue was used. (Unless the over-zealous banishment of a goto resulted in a needless exception being thrown; in which case the removing the goto would degrade performance.)
Perhaps I didn't say it very well. What I intended to say was this:
Dijkstra's "Go To Statement Considered Harmful" letter to the CACM was written some 55 years ago; at a time when many of the widely used programming languages did not have (or had limited forms of) the kind control flow constructs that we now routinely use. Dijkstra's main point was that languages should support better control structures than what was prevalent at that time. And that programmers who were moving to the newer languages should start using the newer control flow constructs.
In C/C++ code, "goto" is limited to the scope of a single function (unlike setjmp and longjmp), and the control flow is as easy to follow as a continue or break. Unless the function has 237 lines of code; in which case just eliminating a "goto" does nothing to make the code better. Bad programmers write bad code; and the magic wand of banish "goto" is not going to change that.
"goto" is one of the many tools in the toolset, and it can be abused; one could even say that it has a proclivity towards being abused. There are people who believe that a lot of other tools too are unmitigated evil - pointers, operator overloading, exceptions, static members, metaprogramming, C++ ... Any useful tool is used well by people who know how to use it, and abused by people who don't.
Over a short distance with meaningful labels, "goto" can be as (sometimes more) effective, clean and understandable than an assemblage of flags in nested looping constructs.
Would this real-life (so I believe, it was on the internet, in a discussion of goto) C code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
|
int parse()
{
Token tok ;
reading:
tok = gettoken() ;
if( tok == END ) return ACCEPT ;
shifting:
if( shift(tok) ) goto reading ;
reducing:
if( reduce(tok) ) goto shifting ;
return ERROR ;
}
|
become simpler or more elegant if we banished the gotos?
If while writing C++, I find myself considering the use of a "goto", there are these possibilities:
a. I have written bad code; I need to take a hard look at it; see how it can be restructured (most likely).
b. "goto" is the simplest, most elegant way in which I can express the intent of this code (less likely).
c. Somehow, anyhow, just eliminate that evil "goto", and my grotesque code will magically transmogrify itself into an art form of sublime beauty (so unlikely, that this situation is almost non-existent.)
My suggestion to beginners would be:
If you find yourself using a "goto", have a re-look at the structure of your code; chances are that it can be improved.