Neal Becker wrote: > I have an object that expects to call a callable to get a value: > > class obj: > def __init__ (self, gen): > self.gen = gen > def __call__ (self): > return self.gen()
As written, there is no need for this "obj" class, it just adds a pointless layer of indirection. Perhaps it was written by a Java programmer? http://steve-yegge.blogspot.com.au/2006/03/execution-in-kingdom-of-nouns.html Instead of: x = obj(something_callable) # later result = x() just do: x = something_callable result = x() or even result = something_callable() > Now I want gen to be a callable that repeats N times. What happens on the sixth time? The world ends? Most callables can be called indefinitely. I'm going to assume an exception. Later I'll use a RuntimeException, but you can do anything you like. > I'm thinking, this sounds perfect for yield > > class rpt: > def __init__ (self, value, rpt): > self.value = value; self.rpt = rpt > def __call__ (self): > for i in range (self.rpt): > yield self.value > > so I would do: > > my_rpt_obj = obj (rpt ('hello', 5)) > > to repeat 'hello' 5 times (for example). > > But this doesn't work. when obj calls self.gen(), that returns a > generator, not the next value. > > How can I make this work? I can't change the interface of the existing > class obj, which expects a callable to get the next value. The built-in function `next` almost does what we want, except the exception raised is inappropriate. Unless you are very careful, you don't want to allow StopIteration to propagate, lest it be caught in an unexpected place and cause surprises. (Not the pleasant kind.) py> from functools import partial py> f = partial(next, rpt("hello", 2)()) # note the extra parens py> f() 'hello' py> f() 'hello' py> f() Traceback (most recent call last): File "<stdin>", line 1, in <module> StopIteration But I wouldn't use rpt as given. I'd say: def repeat(obj, count): for i in range(count): yield obj raise RuntimeError # or whatever mycallable = partial(next, repeat("hello", 5)) # no extra parens And now pass mycallable to your other class. P.S. your naming conventions give me a blood clot. Class "rpt" taking an argument "rpt" -- I lost six months of life just from reading that. -- Steven -- https://mail.python.org/mailman/listinfo/python-list