'''Q.''' Why doesn't TCL have a 'goto' command? '''A.''' ([Donal Fellows]) Because "goto"s are the bane of structured programming. Let's examine what you might use them for: 1) Implementing a standard control structure. This simply doesn't fit with the Tcl way of doing things. Remember, [[if]], [[for]] and [[while]] are all ordinary commands with no special privileges. If you want, you can even create your own control structures which are just as much a part of the language as they are. proc repeat {script untilKeyword expression} { if {![string equal $untilKeyword "until"]} { return -code error "malformed repeat: should be \"repeat\ script until expression\"" } uplevel 1 $script set test [list expr $expression] while {![uplevel 1 $test]} { uplevel 1 $script } } 2) Resource cleanup on error exit. Most Tcl resources are cleaned up automatically on exit from scope. The rest can be handled with the use of [[catch]] or something built on top of it; it is a better way to do it too, as it is writing code that is saying what you actually mean. (Alas, the code for try/finally is a bit too long for me to reproduce here.) ''KBK'' (8 November 2000) -- Here's one possible implementation of [try ... finally ...] [KPV] another C idiom for doing this to use 'do { ... } while(0);'. Inside that loop you have breaks, which essentially are goto's to the end of the loop. 3) Creating a state-machine. It is equally possible to use a mechanism based on Tcl arrays and [[eval]] to do this, like this: array set transition { initialState state1 state1 { set state state2 set x 1 } state2 { set state state3 incr x $x } state3 { set state [expr {($x < 10) ? "state2" : "state4"}] } state4 { break } } set state $transition(initialState) while {1} {eval $transition($state)} puts $x ;# Can you guess what this does without running the code? This can even be extended fairly easily into working over events. I leave that as an exercise though. 4) Err. I can't think of a 4) at the moment. :^) As you can see, you can do a lot with Tcl even without a goto. It often even ends up clearer to the person maintaining the code like that. Everyone's a winner! ---- [David Cuthbert] comments on 4): If you're a code generator, you'll often use a goto for a combination of the above reasons. Of course, if you're a code generator, you're not human, and your code is not intended to be read by humans. You're also probably spitting out C or assembly instead of Tcl. :-) ---- [KPV] more comments on 4) In C, I've had to use a goto to break out of multiple loops. Newer languages have labeled loops and you can break to a label. For example: for (i = 0; i < 100; ++i) { for (j = 0; j < 100; ++j) { if (IsFound(i,j)) goto found; } } :found ulis,2002-09-03: You can easily have break labels in Tcl. See: http://mini.net/tcl/3402. ---- [SS] Also note that you don't need [break] to exit from switch branches (like in C), so one of the uses of goto in C (to exit a [while] loop that contains [switch]) is a non-issue in Tcl: while(1) { x = get_next_x_value(); switch(x) { case 1: ....; break case 2: ....; break case 3; goto out; } } out: something(); In Tcl a [break] inside the [switch] will exit the while loop in similar code. Also note that in [C] is natural to have [goto], because C maps quite directly to machine language, that's not the case of a scripting language like Tcl, this is why I use [goto] in [C] quite often, and I'm sure the way I use it makes the code more clear instead of spaghetti, but at the same time I don't want goto in Tcl because I feel it useless and probably dangerous for the code quality. History corner: on 1993-05-21, [JO] posted in c.l.t. [http://groups.google.com/groups?q=group:comp.lang.tcl+author:ousterhout&start=800&hl=de&lr=&newwindow=1&scoring=d&selm=1tj4i6%24116%40agate.berkeley.edu&rnum=837] : "Actually I don't have a strong philosophical objection to goto. I think that goto's should be used very sparingly, but there are definitely situations where programs are a lot clumsier without them. The reason they're not in Tcl is that I haven't been able to figure out how to implement them (the structure of Tcl and its interpreter make it hard to skip backwards or forwards)." -------------------------------------------------------------------------------- ---- Also, see [Goto in Tcl].