while ... wend in Tcl Please contribute to this section Don't be silly. while {some_expression_is_true} { do stuff } That's it. ---- [RS] 2005-10-17: [While] this page is not really topical to [Tcl], it illustrates the first generation, if you will, of denoting blocks in programming languages. 0. The oldest languages (Assembler, Fortran etc.) didn't have explicit blocks at all. Only with JMP/GOTO could branching over parts of code be accomplished. 1. ALGOL introduced keywords to mark beginning and end of blocks, where the closing keyword often was the beginning keyword in reverse: if ... fi do ... od I think Unix shells extended this to ''case ... esac'' (but used ''do .. done'' for a change), but nobody seems to have used ''elihw'' for an end of while loop. Instead, some other combinations were introduced: for ... next if ... endif (or End If in VB) Do ... Loop (VB) Select Case ... End Case While ... Wend (VB) while do ... od (Maple) for : ... endfor (Metafont) 2. The [Pascal] language introduced a more orderly grouping, in which ''begin .. end'' were put around every block, no matter if part of a control structure, a function body, etc. 3. Finally (?), [C] simplified this to just use braces: { ... }, and Tcl follows that simplest of all methods. ''([DKF]: Though the use of braces means something else strictly (a particular style of quoting). It just happens to make working with "blocks" incredibly natural.)'' [NEM] Let's not forget [Python] and [Haskell], that use indentation to signify blocks, e.g. (Haskell): main = do putStr "Enter name: " name <- getLine putStr "Hello, " putStrLn name You can also use braces and semi-colons in Haskell if you don't like indentation. Also, somewhat related are [Ruby] and [Smalltalk]'s blocks/[closures]/thunks, where there is special syntax for creating [lambda]s, such as ([Ruby]): list = [1,2,3,4,5,6,7,8,9,10] sum = 0 list.each() {|i| sum = sum + 1 } puts sum Blocks can be seen as being lambdas/closures, either with no params (as in C blocks), or with some parameters defined (as in let-blocks in Lisp and other languages). Using closures has the advantage that the environment is captured properly, so you shouldn't need to mess with something like [uplevel] to sort out scope. Tcl's brace-quoted strings, blocks in Ruby/Smalltalk (and general higher-order programming), monads in Haskell, and macros in [Lisp] all cover a similar kind of ground in terms of allowing code to be passed around, which goes quite a bit beyond what simple blocks provide. (How much cooler would C be if blocks were first-class?) [RS] Do you mean, a mini-closure like this? proc with {argl body args} { foreach $argl $args break eval $body } % with {a b} {expr $a+$b} 3 4 7 % interp alias {} sum {} with {a b} {expr $a+$b} sum % sum 11 31 42 [NEM] That's just [lambda] again, surely? A full closure captures the environment of its definition, so that you can do stuff like: set a 0 map [lambda {x} { incr a $x }] $list puts "total = $a" You can implement this kind of thing in Tcl by writing a [[lambda]] function that captures the environment (either selectively as in [Jim]'s statics, or the entire thing via introspection: [[info locals]]). It's not as nice as having special syntax for it, though. ---- [Category Control Structure]