Version 1 of Nested-loop join

Updated 2002-11-27 20:00:37

Richard Suchenwirth 2002-11-27 - A visitor in the Tcl chatroom asked for a modified foreach to cover all combinations of the input lists. In database technical terms, this is called a "nested-loop join", at least one functional programming tutorial tells me so.

Well, and reason enough to do some Tcl'ing (where metaprogramming is as trivial as virtual destructors in other languages ;-) - from the input, build up a nested command of foreaches, insert the specified body in the middle, and presto:

 proc nljoin args {
    set body [lindex $args end]
    set cmd ""
    foreach {vars list} [lrange $args 0 end-1] {
       append cmd "[list foreach $vars $list] \{\n"
       append body "\}"
    }
    uplevel 1 $cmd$body
 }

#------------------------- Testing:

 % nljoin x {a b} y {c d} {puts x:$x,y:$y}
 x:a,y:c
 x:a,y:d
 x:b,y:c
 x:b,y:d

No error-checking yet - the length of args must be odd and >2. Caveat user.

Filtering the lists in advance reduces the runtime needed - for instance, after an example in [?], to get the list of all professors who have published since 1990, using the fancy all list comprehension:

 nljoin pub [all x from publications where {$date($x)>=1990}] \
        prof [all x from staff where {$status($x)=="professor"}] {
            if {$empID($pub)==$empID($prof)} {
                lappend res $prof
            }
        }

Category Concept | Arts and crafts of Tcl-Tk programming