Hacker Newsnew | past | comments | ask | show | jobs | submitlogin

I struggle with how you claim my "analysis is wrong", and then basically reiterate my entire point. I know it's not that badly written; other people got it just fine and complain about what it actually does say.

The modern goto is not the one he wrote about. It is tamed and fits into the structured programming paradigm. Thus, ranting about goto as if it is still the 1960s is a pointless waste of time. Moreover, even if it does let you occasionally violate structured programming in the highly restricted function... so what? Wrecking one function is no big deal, and generally used when it is desirable that a given function not be structured programming. Structured programming, as nice as it is, is not the only useful paradigm. In particular state machines and goto go together very nicely, where the "state machine" provides the binding paradigm for the function rather than structured programming. It is perhaps arguably the distinctive use case that it lives on for in modern languages.



> The modern goto is not the one he wrote about. It is tamed and fits into the structured programming paradigm.

No, it doesn't, not the goto of C or C++ (which tames it a smidge because it has to). That's the disconnect you have. It's not fine just because you can't go too crazy and smash other functions with it anymore. You can still go crazy and jump into the middle of scopes with uninitialized variables. You can still write irreducible loops with it, which I would argue ought to be grounds for the compiler to rm -rf your code for you.

There are tame versions of goto--we call them break, continue, and return. And when the C committee discussed adding labeled break, and people asked why it was necessary because it's just another flavor of goto, I made some quite voluminous defense of labeled break because it was a tame goto, and taming it adds more possibility.

And yes, the tame versions of goto violate Dijkstra's vision. But I also don't think that Dijkstra's vision is some sacrosanct thing that must be defended to the hilt--the tame versions are useful, and you still get most of the benefits of the vision if you have them.

In summary:

a) when Dijkstra was complaining about goto, he would have included the things we call break, continue, and early return as part of that complaint structure.

b) with the benefit of decades of experience, we can conclude that Dijkstra was only partially right, and there are tame goto-like constructs that can exist

c) the version of goto present today in C is still too untamed, and so Dijkstra's injunction against goto can apply to some uses of it (although, I will note, most actual uses of it are not something that would fall in that category.)

d) your analysis, by implying that it's only the cross-function insanity he was complaining about, is wrong in that implication.


"You can still go crazy and jump into the middle of scopes with uninitialized variables."

It is difficult when speaking across languages, but in many cases, no, you can't.

https://go.dev/play/p/v8vljT91Rkr

C isn't a modern language by this standard, and to the extent that C++ maintains compatibility with it (smoothing over a lot of details of what that means), neither is it. Modern languages with goto do not generally let you skip into blocks or jump over initializations (depending on the degree to which it cares about them).

The more modern the language, generally the more thoroughly tamed the goto is.


It doesn't even need to be a modern language to protect against that:

  BEGIN
    INT x := 1;
    print(("x is", x, newline));

    GOTO later;

    INT y := 2;

   later:

    print(("y is", y, newline))
  END
for which we have:

  $ a68g goto.a68 
  x is         +1
  11           print(("y is", y, newline))
                            1           
  a68g: runtime error: 1: attempt to use an uninitialised REF INT value (detected in [] "SIMPLOUT" collateral-clause starting at "(" in this line).
Although admittedly it is a runtime error.

However if y is changed to 'INT y = x + 2;', essentially a "constant", then there is no runtime error:

  $ a68g goto.a68 
  x is         +1
  y is         +0




Consider applying for YC's Summer 2026 batch! Applications are open till May 4

Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: