[Python-ideas] Anonymous blocks (again):

Martin Morrison mm at ensoft.co.uk
Mon May 13 22:43:00 CEST 2013


On 13 May 2013, at 03:53, "Stephen J. Turnbull" <stephen at xemacs.org> wrote:

> Martin Morrison writes:
> 
>> That is instead of a decorator-like syntax, make the "in" keyword
>> reusable to introduce a new block, whose "argument" is a statement
>> that can forward reference some names, which are then defined
>> within the block. This allows multiple temporary names to be
>> defined (each in a separate statement within the block).
> 
> This idea and its presumed defects are described (using the "given"
> syntax of PEP 3150) in the section "Using a nested suite" in PEP 403.

[Thanks for pointing this out - I seemed to miss the crux of that in my first reading]

The general argument against seems to be that it makes implementation difficult, and PEP3150 has (what to me is) very awkward syntax involving leading dots, etc. to try to help the implementation. This feels wrong to me (sacrificing functionality/clarity for ease of implementation - at least during the first pass). Also, would it not be possible to implement it something like:

in <stmt>:
    <suite>

Becomes:

_locals = dict()
exec(<suite>, globals(),  _locals)
_composed = MagicDict(write_to=locals(), first_read_from=_locals)
exec(<stmt>, globals(), _composed)
del _locals, _composed

(to clarify: MagicDict is some way of composing two dicts so that write operations always go to a specific dict, but read operations first go to another dict. i.e. Names are first looked up in the temporary locals created from the suite, then in the 'real' locals, but all new name bindings go into the actual local scope)

There may need to be some special handling for 'nonlocal' if required, but 'global' should Just Work. Also there is no need for any of the statement restrictions discussed in PEP3150.

>> Some further thought is required on whether only def (and maybe
>> class) statements should be allowed within the "in" block. Although
>> I guess there's technically nothing wrong with:
>> 
>> in x = y + z:
>>    y = 12
>>    z = 30
>> 
>> Other than it's a very verbose way of doing something simple. ;-)
> 
> Violates TOOWTDI according to PEP 403.

Inherently since the attempt of these PEPs is to reorder some code, they violate TOOWTDI. However, the reordering provides substantial benefits to readability. In that sense, they are very much like decorators (and thus I can see why some attempt was made to align the syntaxes).

In any case, TOOWTDI refers to only one *obvious* way to do it (at least obvious if you are Dutch ;-)). 

> David Mertz and Juancarlo Añez riff on the theme:
> 
>> [Why not spell it something like]:
>> 
>> in x = do_something(in_arg, success_hdlr, error_hdlr, const) let:
>>    def success_hdlr(result):
>>        ... # Do something with result
>>    def error_hdlr(error):
>>        ... # Do something with error
>>    const = 42
> 
> (Note the "let" at the end of the "in" clause.)
> 
> Python doesn't use redundant keywords for a single construct.
> "let" is redundant with the following "def"s.  On top of that, "let"
> being a new keyword will kill this syntax, I think.

Agreed. I also prefer a prefix (in my example "in") over the "given" or "let" postfix. It makes it obvious as I approach the construct that it is going to do something different, rather than requiring me to look at the end of the line to see the colon. cf. with, for, while, if - in fact all complex statements.

Cheers,
Martin


More information about the Python-ideas mailing list