Version 6 of tcl9var

Updated 2006-09-27 13:02:06 by NEM

if false {

wdb Inspired by If we had no variables, and some ideas found in Tcl 9.0 WishList, I have some day-dreams of getting rid of set, where instead of the procedure set the variable itself is a procedure.

instead of saying

 % set a apple
 apple
 %

we could say

 % tcl9var a apple
 apple
 %

and instead of saying

 % puts "my $a is red"
 my apple is red
 %

we could say

 % puts "my [a] is red"
 my apple is red
 % 

and instead of changing the variable a by saying

 % set a ${a}tree
 appletree
 %

we could say

 % a becomes [a]tree
 appletree
 %

Here is a toy implementation of such behaviour:

 }

 set persistentCounter 0
 array set persistent {}

 proc tcl9var {name value} {
    variable persistentCounter
    variable persistent
    set persistent([incr persistentCounter]) $value
    uplevel 1 [subst {
        proc $name {{cmd get} args}\
            {eval ::handleVar $persistentCounter \$cmd \$args}
    }]
    set persistent($persistentCounter)
 }

 proc handleVar {count cmd args} {
    variable persistent
    switch -exact -- $cmd {
        get {
            set persistent($count)
        }
        set - = - <- - becomes {
            eval set persistent($count) $args
        }
        append - lappend {
            eval $cmd persistent($count) $args
        }
        + - - - * - / - % - ** - 
        < - <= - > - >= - == - != {
            expr "$persistent($count) $cmd $args"
        }
        default {
            eval $cmd $persistent($count) $args
        }
    }
 }

 if false {

Possibilities -- see source of proc handleVar above. Variables behave like objects.

Consequences -- closures must handle namespace of procedures instead of variables. Differs from current behaviour where procedures defined globally and procedures defined in current namespace are visible.

Incompatibilities with set -- variables and procedures use the same namespace, so it is not possible to give a var the name of an existing procedure.

Summary -- just a day-dream. (What's wrong with day-dreams? Who said, man will never fly?)

 }

NEM Added a -exact to the switch, to avoid treating * etc as glob characters. Nicely done -- this is exactly the sort of thing I'd like to see. The main problem, as you state in your "consequences" section, is that procs have local vars, but not local commands. I think Lars H may have suggested proc-local commands at one point, and to my shame I think I thought they were a bad idea!