[Python-ideas] PEP 530: Asynchronous Comprehensions

Koos Zevenhoven k7hoven at gmail.com
Wed Sep 7 10:57:37 EDT 2016


On Wed, Sep 7, 2016 at 3:27 PM, Nick Coghlan <ncoghlan at gmail.com> wrote:
[...]
>
> The new issue that's specific to comprehensions is that the statement
> form doesn't have the confounding factor of having an expression to
> the left of it. Thus, the prefix is unambiguous and can be read as
> modifying the entire statement rather than just the immediately
> following keyword:
>
>     async for row in db.execute(...):
>         process(row)
>
> It's also pragmatically necessary right now due to the sleight of hand
> that Yury used in the code generation pipeline to bring in "async
> def", "async with", and "async for" without a __future__ statement,
> but without making them full keywords either.

I don't think this issue strictly has anything to do with where that
"async" is put in the syntax, as long as it's used within the
definition of an async function:

async def function():
    # in here, is effectively "async" a keyword.

Of course, in French, this would be:

def function async():
    # dedans, "async" est effectivement un mot clé

I'm sure someone will be able to correct my French, though.

[and Nick writes:]
>     [process(row) async for row in db.execute(...)]
>
> When reading that, is "async" a postfix operator being used in a
> normal comprehension (wrong, but somewhat plausible)? Or is it part of
> a compound keyword with "for" that modifies the iteration behaviour of
> that part of the comprehension (the correct interpretation)?
>
>     [(process(row) async) for row in db.execute(...)]
>     [process(row) (async for) row in db.execute(...)]
>
> The postfix operator interpretation is just plain wrong, but even the
> correct interpretation as a compound keyword sits between two
> expressions *neither* of which is the one being modified (that would
> be "db.execute()")
>
> By contrast, if the addition of full async comprehensions is deferred
> to 3.7 (when async becomes a true keyword), then the infix spelling
> can be permitted in both the statement and comprehension forms:

That's an interesting suggestion. What exactly is the relation between
deferring this PEP and permitting the infix spelling?

This would make it more obvious at a first glance, whether something
is a with statement or for loop. The word "async" there is still not
very easy to miss, especially with highlighted syntax.

I didn't realize (or had forgotten) that PEP 492 is provisional.

>     for row in async db.execute(...):
>         process(row)
>
>     [process(row) for row in async db.execute(...)]
>
> with the prefix spelling of the statement form retained solely for
> backwards compatibility purposes (just as we retain "from __future__
> import feature" flags even after the feature has become the default
> behaviour).
>
> The beauty of the infix form is that it *doesn't matter* whether
> someone reads it as a compound keyword with "in" or as a prefix
> modifying the following expression:
>
>     [process(row) for row (in async) db.execute(...)]
>     [process(row) for row in (async db.execute(...))]
>
> In both cases, it clearly suggests something special about the way
> "db.execute()" is going to be handled, which is the correct
> interpretation.

And db.execute is an async iterarable after all, so "async" is a
suitable adjective for db.execute(...).

-- Koos

[...]
>
> Cheers,
> Nick.
>
> --
> Nick Coghlan   |   ncoghlan at gmail.com   |   Brisbane, Australia
> _______________________________________________
> Python-ideas mailing list
> Python-ideas at python.org
> https://mail.python.org/mailman/listinfo/python-ideas
> Code of Conduct: http://python.org/psf/codeofconduct/



-- 
+ Koos Zevenhoven + http://twitter.com/k7hoven +


More information about the Python-ideas mailing list