Numerical array processing in pure Tcl

Arjen Markus (15 november 2023) I have been playing with the idea for a long time, but then I had some time to spend on it: have [expr] work on lists of data, via pure Tcl. Well, the code below is merely a proof of concept, I have no idea if it is practical or performant or what. And it will never beat compiled extensions like vectcl. But then, it is not meant to.

Just consider it a vain attempt by a long-time Tcler to bring a flavour of numerical array processing into Tcl without having to compile code. It is, partly indeed, showing off how flexible Tcl really is.

# array_expr.tcl --
#     Array expressions in pure Tcl?
#

# lexpr --
#     Evaluate an expression which contains lists of numbers
#
# Arguments:
#     expression        Expression to be evaluated
#
# Result:
#     The value of the expression with the numbers filled in
#     one by one. In general, this will be a list of values.
#
# Example:
#     set a {1 2 3}
#     puts [lexpr {2*$a}]
#     ==> {2 4 6}
#
proc lexpr {expression} {

    #
    # Examine the expression: scalars and arrays
    #
    set names [regexp -inline -all {\$[A-Za-z0-9_]+} $expression]

    set foreachVars {}
    foreach name $names {
        set name [string range $name 1 end]
        upvar 1 $name __$name
        if { [llength [set __$name]] > 1 } {
            lappend foreachVars $name [set __$name]
        } else {
            set $name [set __$name]
        }
    }

    if { [llength $foreachVars] > 0 } {
        set __result {}

        foreach {*}$foreachVars {
            lappend __result [expr $expression]
        }
        return $__result
    } else {
        expr $expression
    }
}

# And test the idea ...

set a {1 2 3}
set b {1 0 3}
set c 1
puts [lexpr {tan($a) + $b + $c}]

set d 1
puts [lexpr {tan($d) + $c}]

NR - 2023-11-16 11:46:42

Just an opinion, but I find that the most boring to write in an expression in Tcl is the '$' attached to each variable, I find the idea of vectcl very interesting not to use them. In any case, thank you for this example.


arjen - 2023-11-17 07:41:30

Indeed, vectcl is a wonderful extension - the code I posted is not at all meant as an alternative. The challenge for me was whether I could do this in pure Tcl and it turned out to be much simpler than I expected. The advantage of it being pure Tcl is that you do not need to rely on the pacakge being available on your particular platform, but that is really just a small convenience.


Bocaj22 - 2023-11-22 01:45:40

Impressive. This makes me wonder if a similar approach could extend expr to handle matrix math as well, while staying in pure tcl.