[Python-ideas] Fwd: Fwd: Fwd: unpacking generalisations for list comprehension

David Mertz mertz at gnosis.cx
Sun Oct 16 10:40:39 EDT 2016


On Sun, Oct 16, 2016 at 5:34 AM, Sven R. Kunze <srkunze at mail.de> wrote:

> On 16.10.2016 07:08, David Mertz wrote:
>
>> In case it wasn't entirely clear, I strongly and vehemently opposed this
>> unnecessary new syntax. It is confusing, bug prone, and would be difficult
>> to teach.
>
>

> "Whom does he teach? Children?"
> Me: "What? No, everybody I think. Why?"
> She: "It's easy enough to remember what the star does."
>

As I've said, the folks I teach are mostly working scientists with
doctorates in scientific fields and years of programming experience in
languages other than Python.  For example, rocket scientists at NASA.

Now I admit that I don't specifically know how quickly they would pick up
on something I've never taught them.  But I've written enough teaching
materials and articles and books and I have a certain intuition.  The way
you explained the special case you built up is pretty good, but it's very
tailored to making that specific case plausible, and is not general.


> She also asked what would the alternative would look like. I wrote:
> """
> >>> from itertools import chain
> >>> list(chain.from_iterable((i,i,i) for i in range(4)))
> [0, 0, 0, 1, 1, 1, 2, 2, 2, 3, 3, 3]
> """
> Her reaction was like: "That's supposed to be easy to remember? I find the
> star easier."
>

That is an absolutely terrible construct, obviously.  I have to pause and
think a while myself to understand what it does.

It also answers a very different use case than the one that has been mostly
discussed in this thread.  A much better spelling is:

>>> [i for i in range(4) for _ in range(3)]
[0, 0, 0, 1, 1, 1, 2, 2, 2, 3, 3, 3]

For some related uses, itertools.repeat() is very useful.

But the case that has been discussed far more often is like this:

>>> listOfLists = [[1,2,3], [4,5,6,7], [8,9]]
>>> flatten(listOfLists)

The very long argument is that somehow that would be easier to spell as:

>>> [*i for i in listOfLists]

It's just not easier.  And there are contrary intuitions that will occur to
many people based on the several other related-but-different uses of * for
packing/unpacking in other contexts.

Also, this simplest case might be teachable, but the more general "exactly
where can I use that star in a comprehensions" will be far harder to
explain plausibly.  What's the pattern here?

>>> [(*i,) for i in listOfLists]
[(1, 2, 3), (4, 5, 6, 7), (8, 9)]
>>> [(i,*i) for i in listOfLists]
[([1, 2, 3], 1, 2, 3), ([4, 5, 6, 7], 4, 5, 6, 7), ([8, 9], 8, 9)]
>>> [(*i,*i) for i in listOfLists]
[(1, 2, 3, 1, 2, 3), (4, 5, 6, 7, 4, 5, 6, 7), (8, 9, 8, 9)]
>>> [*(i,) for i in listOfLists]
# ... no clear intuition here ...
>>> [*(*i) for i in listOfLists
# ... even more confusing ...

Yes! I know those first few are actually doing something different than the
proposed new syntax.

But explaining that to my rocket scientists or your girlfriend in a
consistent and accurate way would be a huge challenge.  It would mostly
come down to "don't do that, it's too confusing."

-- 
Keeping medicines from the bloodstreams of the sick; food
from the bellies of the hungry; books from the hands of the
uneducated; technology from the underdeveloped; and putting
advocates of freedom in prisons.  Intellectual property is
to the 21st century what the slave trade was to the 16th.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/python-ideas/attachments/20161016/5f1a9a59/attachment-0001.html>


More information about the Python-ideas mailing list