Musings about the tcllib generator package
From
Julian H J Loaring@21:1/5 to
All on Tue Mar 29 05:21:34 2022
I am trying to get my head around the Tcllib generator package (version 0.2). It took a while for the penny to drop that generators seem to me to be a bit quantum in that they are changed by observing/accessing them...
In the following snippets, the "foreach" is the one provided by the generator package not the Tcl ::foreach command. Once a foreach loop over a generator, xs, completes, the generator is exhausted so "generator length $xs" will be 0.
~~~~~~~~~~~~~~~~~~~~
1)
In the following interactive session, I notice that "generator head ..." returns a generator, but the value of this generator is empty:
===
% package require generator
0.2
% generator define range {n m} {
for {set i $n} {$i <= $m} {incr i} {
generator yield $i
}
}
::range
% set r [range 21 30]
::generator::generator1
% set h [generator head $r]
::generator::generator2
% puts "<[$h]>"
===
In the underlying definition of the "generator take ..." subcommand:
proc head xs { take 1 $xs }
define take {n xs} {
finally destroy $xs
foreach x $xs {
if {[incr i] >= $n} { break }
yield $x
}
}
I think the inequality test should be >, because, as is, the loop will exit early if n = 1:
define take {n xs} {
finally destroy $xs
foreach x $xs {
if {[incr i] > $n} { break }
yield $x
}
}
2) Conceptually, should "generator head ..." return a generator (like it currently does) or should it return a value?
The latter would require:
proc head xs { takeList 1 $xs }
3) The "generator last ..." returns nothing:
===
% set l [generator last $r]
% puts "<$l>"
===
"generator last ..." is defined as follows:
proc last xs {
foreach x $xs { }
return $x
}
In the above definition, running this loop will exhaust the generator, xs, so the returned x is empty.
So, conceptually, I think "generator last ..." should return a value because every item of the generator must be yielded in order to produce the last
value, exhausting the generator in the process.
Here is a modified version of "generator last ..." which returns the last value of the range:
proc last xs {
set l ""
foreach x $xs { set l $x }
return $l
}
~~~~~~~~~~~~~~~~~~~~
Any comments? I am slowly feeling my way with Functional Programming ideas such as generators, so let me know if I have missed the point!
kind regards
Julian
--- SoupGate-Win32 v1.05
* Origin: fsxNet Usenet Gateway (21:1/5)