coyotes rand mair fheal wrote in the comp.lang.tcl newsgroup:
proc rangedswitch {index switches} { for {set i 0} {$i<[llength $switches]} {incr i} { if {[string equal $switches([expr {$i+1}]) ..]} { set match [expr {$switches($i)<=$index &&$index<=$switches([expr {$i+2}])}] incr i 2 } else { set match [expr {$switches($i)==$index}] } et cetera rangedswitch $i { 0 {do a} 2 .. 5 {do b} }
* Could someone elaborate on this? It won't work as-is. -- Sy / jrandomhacker.info
RS rather reinvented that wheel, slightly different of course - see the test at end:
proc rswitch {value body} { set go 0 foreach {cond script} $body { if {[regexp {(.+)\.\.(.+)} $cond -> from to]} { if {$value >= $from && $value <= $to} {incr go} } else { if {$value == $cond} {incr go} } if $go { uplevel 1 $script break } } if {$cond eq "default" && !$go} {uplevel 1 $script} ;#(1) }
Testing:
% foreach i {0 1 2 3 4 5 6 7 8} {puts $i;rswitch $i {1 {puts yes} 2..5 {puts maybe} 6..8 {puts no}}} 0 1 yes 2 maybe 3 maybe 4 maybe 5 maybe 6 no 7 no 8 no
Due to polymorphic comparison (numeric or string), this also works:^)
% foreach i {A K c z 0 7} { puts $i;rswitch $i {A..Z {puts upper} a..z {puts lower} 0..9 {puts digit}} } A upper K upper c lower z lower 0 digit 7 digit
* Ok, that's useful stuff.. but what about multi-digit numbers? -- Sy / jrandomhacker.info
e.g., using:
rswitch 100 {A..Z {echo upper} a..z {echo lower} 0..999 {echo digit}}
RS Yup, my bug. ".." in regular expressions match any char, so the original version
if {[regexp (.+)..(.+) $cond -> from to]} {
was over-eager - in 0..99, it matched "0." as from, and "9" as to. Fixed above, so multi-digit numbers work (and added a line for default treatment at #(1)). Still missing is fall-through treatment (a - b - c ...} - may come later. Thanks for testing!
Arts and crafts of Tcl-Tk programming | Category Control Structure