Memoizing Generators
Michael Sparks
zathras at thwackety.com
Tue Jul 8 20:39:31 EDT 2003
> Now, the two remaining issues are 1) can we "unify" the generator
> memoization with the "standard" memoization and 2) can we deal with lists
> as well (i.e. my generator was returning tuples ... since I'm scared of
> lists in recursive generator contexts *wink*).
> One other memoization issues: what if the args (which will become
> keys) are mutables ... in particular, lists. I suppose we could just
> tuple() them up?
How would you deal with the following generator? (On the assumption you want a
a general purpose memoisation mechanism :)
def retrieveData(source=None, command=True,blocksize=1024):
if source:
if not command:
fh = open(source, "rb",0)
else:
fh = os.popen(self.command)
else:
fh = sys.stdin
try:
try:
while 1:
data = fh.read(blocksize)
if data:
yield data
else:
raise Finality
except Exception, e:
if source:
fh.close()
raise e
except Finality:
pass
If your source is a network connection, or a real user this becomes further
indeterminate... Not a suggestion to not try, just worth considering :)
The other problem as I see it with your implementation is it expects the
generator to terminate. This is far from guaranteed - generators are useful
for dealing with infinite sequences/lists and working with functions that
might not halt. (eg calculate the best approximation of pi that you can based
on time available, not based on number of iterations/memory available)
eg
def runGenerator(fn,args,timeAlloted):
tstart = time.time()
gen = fn(args).next
r = gen()
while 1:
if time.time()-tstart >=timeAlloted:
break
r = gen()
return r
Consider the possibility that the function is a "next move" in chess and the
time is set by the first player to "hard" - ie lots of time. The next time a
player comes along with the time set to "easy", the memoised version won't be
aware of this in this scenario and returns the hard result (but very
quickly...), or worse hits stop iteration - which the original version
wouldn't. Or even worse - occasionally hits the StopIteration and normally
returns the "hard" result aroung 80-90% of the time.
That said memoising _good_ chess results from certain positions _might_ be
considered a good thing. It's still an issue though.
Regards,
Michael.
More information about the Python-list
mailing list