[Python-ideas] Coming up with an alternative to PEP 505's None-aware operators

Rhodri James rhodri at kynesim.co.uk
Fri Feb 16 09:37:48 EST 2018


On 16/02/18 02:06, Nick Coghlan wrote:
> The recent thread on variable assignment in comprehensions has
> prompted me to finally share
> https://gist.github.com/ncoghlan/a1b0482fc1ee3c3a11fc7ae64833a315 with
> a wider audience (see the comments there for some notes on iterations
> I've already been through on the idea).
> 
> == The general idea ==
> 
> The general idea would be to introduce a *single* statement local
> reference using a new keyword with a symbolic prefix: "?it"
[snip]
> If we did pursue this, then PEPs 505, 532, and 535 would all be
> withdrawn or rejected (with the direction being to use an it-reference
> instead).

I don't think that follows.

> == Examples ==
> 
> `None`-aware attribute access:
> 
>      value = ?it.strip()[4:].upper() if (?it=var1) is not None else None
> 
> `None`-aware subscript access:
> 
>      value = ?it[4:].upper() if (?it=var1) is not None else None
> 
> `None`-coalescense:
> 
>      value = ?it if (?it=var1) is not None else ?it if (?it=var2) is
> not None else var3
> 
> `NaN`-coalescence:
> 
>      value = ?it if not math.isnan((?it=var1)) else ?it if not
> math.isnan((?that=var2)) else var3
 >
> 
> Conditional function call:
> 
>      value = ?it() if (?it=calculate) is not None else default
> 

I have to say I don't find this an improvement on "value = var if var is 
not None else None" and the like.  In fact I think it's markedly harder 
to read.  It has the same repetition problem as the current situation, 
just with added glyphs.

> Avoiding repeated evaluation of a comprehension filter condition:
> 
>      filtered_values = [?it for x in keys if (?it=get_value(x)) is not None]

Definite win here.  It doesn't read particularly naturally, but then 
list comprehensions don't read that naturally either.  I would still 
prefer something that read better.

> Avoiding repeated evaluation for range and slice bounds:
> 
>      range((?it=calculate_start()), ?it+10)
>      data[(?it=calculate_start()):?it+10]
> 
> Avoiding repeated evaluation in chained comparisons:
> 
>      value if (?it=lower_bound()) <= value < ?it+tolerance else 0
> 
> Avoiding repeated evaluation in an f-string:
> 
>      print(f"{?it=get_value()!r} is printed in pure ASCII as {?it!a}
> and in Unicode as {?it}"

While these are wins, they don't read nicely at all.  I still don't see 
what's wrong with

   start = calculate_start()
   values = range(start, start+10)

which beats everything I've seen so far for clarity.


-- 
Rhodri James *-* Kynesim Ltd


More information about the Python-ideas mailing list