[Python-ideas] Fwd: Fwd: unpacking generalisations for list comprehension
Sjoerd Job Postmus
sjoerdjob at sjoerdjob.com
Thu Oct 13 16:40:19 EDT 2016
After having followed this thread for a while, it occured to me that the
reason that the idea is confusing, is because the spelling is confusing.
I think the suggested spelling (`*`) is the confusing part. If it were
to be spelled `from ` instead, it would be less confusing.
Consider this:
g = (f(t) for t in iterable)
is "merely" sugar for
def gen():
for t in iterable:
yield f(t)
g = gen()
Likewise,
l = [f(t) for t in iterable]
can be seen as sugar for
def gen():
for t in iterable:
yield f(t)
l = list(gen())
Now the suggested spelling
l = [*f(t) for t in iterable]
is very confusing, from what I understand: what does the `*` even mean
here.
However, consider the following spelling:
l = [from f(t) for t in iterable]
To me, it does not seem far-fetched that this would mean:
def gen():
for t in iterable:
yield from f(t)
l = list(gen())
It follows the "rule" quite well: given a generator display, everything
before the first "for" gets placed after "yield ", and all the
`for`/`if`s are expanded to suites.
Now I'm not sure if I'm a fan of the idea, but I think that at least the
`from `-spelling is less confusing than the `*`-spelling.
(Unless I totally misunderstood what the `*`-spelling was about, given
how confusing it supposedly is. Maybe it confused me.)
On Fri, Oct 14, 2016 at 03:55:46AM +1100, Steven D'Aprano wrote:
> On Thu, Oct 13, 2016 at 04:34:49PM +0200, Martti Kühne wrote:
>
> > > If I had seen a list comprehension with an unpacked loop variable:
> > >
> > > [t for t in [(1, 'a'), (2, 'b'), (3, 'c')]]
>
> Marttii, somehow you have lost the leading * when quoting me. What I
> actually wrote was:
>
> [*t for t in [(1, 'a'), (2, 'b'), (3, 'c')]]
>
>
> > As it happens, python does have an external consumption operation that
> > happens externally with an iteration implied:
> >
> > for t in iterable:
> > yield t
>
> If you replace the t with *t, you get a syntax error:
>
>
> py> def gen():
> ... for t in [(1, 'a'), (2, 'b'), (3, 'c')]:
> ... yield *t
> File "<stdin>", line 3
> yield *t
> ^
> SyntaxError: invalid syntax
>
> Even if it was allowed, what would it mean? It could only mean "unpack
> the sequence t, and collect the values into a tuple; then yield the
> tuple".
>
>
>
> > For your example [t for t in [(1, 'a'), (2, 'b'), (3, 'c')]] that would mean:
> >
> > for t in [(1, 'a'), (2, 'b'), (3, 'c')]:
> > yield t
> >
> > And accordingly, for the latter case [*t for t in [(1, 'a'), (2, 'b'),
> > (3, 'c')]] it would be:
> >
> > for item in [(1, 'a'), (2, 'b'), (3, 'c')]:
> > for t in item:
> > yield t
>
> No it wouldn't. Where does the second for loop come from? The list
> comprehension shown only has one loop, not nested loops.
>
>
>
> --
> Steve
> _______________________________________________
> 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/
More information about the Python-ideas
mailing list