[Python-ideas] PEP 505 (None coalescing operators) thoughts

Guido van Rossum guido at python.org
Mon Sep 28 21:53:43 CEST 2015


On Mon, Sep 28, 2015 at 12:43 PM, Carl Meyer <carl at oddbird.net> wrote:

> On 09/28/2015 12:38 PM, Guido van Rossum wrote:
> > On Mon, Sep 28, 2015 at 10:38 AM, Carl Meyer <carl at oddbird.net
>
> >     "Propagating" refers to the proposed behavior where use of ?. or ?[
> >     "propagates" through the following chain of operations. For example:
> >
> >         x = foo?.bar.spam.eggs
> >
> >     Where both `.spam` and `.eggs` would behave like `?.spam` and
> `?.eggs`
> >     (propagating None rather than raising AttributeError), simply
> because a
> >     `.?` had occurred earlier in the chain. So the above behaves
> differently
> >     from:
> >
> >         temp = foo?.bar
> >         x = temp.spam.eggs
> >
> >     Which raises questions about whether the propagation escapes
> >     parentheses, too:
> >
> >         x = (foo?.bar).spam.eggs
> >
> > Oh, I see. That's evil.
> >
> > The correct behavior here is that "foo?.bar.spam.eggs" should mean the
> > same as
> >
> >     (None if foo is None else foo.bar.spam.eggs)
> >
> > (Stop until you understand that is *not* the same as either of the
> > alternatives you describe.)
>
> I see that. The distinction is "short-circuit" vs "propagate."
> Short-circuit is definitely more comprehensible and palatable.
>

Right.


> [snip]
> > It should not escape parentheses.
>
> Good. I assume that the short-circuiting would follow the precedence
> order; that is, nothing with looser precedence than member and index
> access would be short-circuited. So, for example,
>
>     foo?.bar['baz'].spam
>
> would short-circuit the indexing and the final member access, translating
> to
>
>     foo.bar['baz'].spam if foo is not None else None
>
> but
>
>     foo?.bar or 'baz'
>
> would mean
>
>     (foo.bar if foo is not None else None) or 'baz'
>
> and would never evaluate to None. Similarly for any operator that binds
> less tightly than member/index access (which is basically all Python
> operators).
>

Correct. The scope of ? would be all following .foo, .[stuff], or .(args)
-- but stopping at any other operator (including parens).


> AFAICS, under your proposed semantics what I said above is still true, that
>
>     x = foo?.bar.baz
>
> would necessarily have a different meaning than
>
>     temp = foo?.bar
>     x = temp.baz
>
> Or put differently, that whereas these two are trivially equivalent (the
> definition of left-to-right binding within a precedence class):
>
>     foo.bar.baz
>     (foo.bar).baz
>
> these two are not equivalent:
>
>    foo?.bar.baz
>    (foo?.bar).baz
>

Right.


> I'm having trouble coming up with a parallel example where the existing
> short-circuit operators break "extractibility" of a sub-expression like
> that.
>

Why is that an interesting property?


> I guess this is because the proposed short-circuiting still "breaks out
> of the precedence order" in a way that the existing short-circuiting
> operators don't. Both member access and indexing are within the same
> left-to-right binding precedence class, but the new operators would have
> a short-circuit effect that swallows operations beyond where normal
> left-to-right binding would suggest their effect should reach.
>
> Are there existing examples of behavior like this in Python that I'm
> missing?


I don't know, but I think you shouldn't worry about this.

-- 
--Guido van Rossum (python.org/~guido)
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/python-ideas/attachments/20150928/600f73ca/attachment-0001.html>


More information about the Python-ideas mailing list