[Python-ideas] Cofunctions PEP - Revision 4
ncoghlan at gmail.com
Wed Aug 11 11:37:35 CEST 2010
On Wed, Aug 11, 2010 at 6:03 PM, Greg Ewing <greg.ewing at canterbury.ac.nz> wrote:
> is evaluated by first checking whether the object ``f`` implements
> a ``__cocall__`` method. If it does, the cocall expression is
> equivalent to
> yield from f.__cocall__(*args, **kwds)
> except that the object returned by __cocall__ is expected to be an
> iterator, so the step of calling iter() on it is skipped.
I think I'd like to see this exist for a while as:
yield from f.cocall(*args, **kwds)
for a while after PEP 380 is implemented before it is given syntactic sugar.
Similar to my other suggestion, a @cofunction decorator could easily
provide a cocall method without implementing __call__.
The compiler wouldn't pick up usages of f.cocall() without yield from
with this approach, but tools like pychecker and pylint could
certainly warn about it.
> If ``f`` does not have a ``__cocall__`` method, or the ``__cocall__``
> method returns ``NotImplemented``, then the cocall expression is
> treated as an ordinary call, and the ``__call__`` method of ``f``
> is invoked.
> Objects which implement __cocall__ are expected to return an object
> obeying the iterator protocol. Cofunctions respond to __cocall__ the
> same way as ordinary generator functions respond to __call__, i.e. by
> returning a generator-iterator.
You want more than the iterator protocol - you want the whole
generator API (i.e. send() and throw() as well as __next__()).
> Certain objects that wrap other callable objects, notably bound methods,
> will be given __cocall__ implementations that delegate to the underlying
If you use a @cofunction decorator, you can define your own descriptor
semantics, independent of those for ordinary functions.
> The use of a decorator instead of ``codef`` was also suggested, but the
> proposal makes this unnecessary as well.
I'm not sure that is really an advantage, given that using a decorator
gives much greater control over the way cofunctions behave.
> It has been questioned whether some combination of decorators and functions
> could be used instead of a dedicated ``cocall`` syntax. While this might be
> possible, to achieve equivalent error-detecting power it would be necessary
> to write cofunction calls as something like
> yield from cocall(f)(args)
> making them even more verbose and inelegant than an unadorned ``yield
> It is also not clear whether it is possible to achieve all of the benefits
> the cocall syntax using this kind of approach.
As far as I can see, the only thing dedicated syntax adds is the
ability for the compiler to detect when a cofunction is called without
correctly yielding control. But pylint/pychecker would still be able
to do that with a decorator based approach.
I'd really want to see a nice clean @cofunction decorator approach
based on PEP 380 seriously attempted before we threw our hands up and
said new syntax was the only way.
Nick Coghlan | ncoghlan at gmail.com | Brisbane, Australia
More information about the Python-ideas