[Python-ideas] If branch merging
Chris Angelico
rosuav at gmail.com
Sun Jun 7 17:29:01 CEST 2015
More information about the Python-ideas mailing list
Sun Jun 7 17:29:01 CEST 2015
- Previous message (by thread): [Python-ideas] If branch merging
- Next message (by thread): [Python-ideas] If branch merging
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]
On Mon, Jun 8, 2015 at 1:04 AM, <random832 at fastmail.us> wrote: > > On Sun, Jun 7, 2015, at 08:20, Chris Angelico wrote: > > with expr as name: > > except expr as name: > > if expr as name: > > > > Three parallel ways to do something and capture it. It makes > > reasonable sense > > The problem is, "with" and "except" create a variable whose scope is > limited to the enclosed block. The proposed "if... as..." does not, so > it's misleading. Actually, they don't. A with block tends to create a broad expectation that the object will be used within that block, but it isn't scoped, and sometimes there's "one last use" of something outside of the block - for instance, a Timer context manager which uses __enter__ to start timing, __exit__ to stop timing, and then has attributes "wall" and "cpu" to tell you how much wall time and CPU time were used during that block. There are a lot of context managers that might as well have disappeared at the end of the with block (open files, psycopg2 cursors (but not connections), thread locks, etc), but they are technically still around. The "except" case is a slightly different one. Yes, the name is valid only within that block - but it's not a matter of scope, it's a deliberate unsetting. >>> e = 2.718281828 >>> try: 1/0 ... except Exception as e: pass ... >>> e Traceback (most recent call last): File "<stdin>", line 1, in <module> NameError: name 'e' is not defined There's no concept of nested/limited scope here, although I'm sure that this particular case could be turned into a subscope without breaking anyone's code (I honestly cannot imagine there being ANY code that depends on the name getting unset!), if Python ever grows support for subscopes that aren't associated with nested functions. Comprehensions do actually create their own scopes, but that's actually implemented with a function: >>> e = 2.718281828 >>> [e*2 for e in range(3)] [0, 2, 4] >>> e 2.718281828 >>> dis.dis(lambda: [e*2 for e in range(3)]) 1 0 LOAD_CONST 1 (<code object <listcomp> at 0x7fa4f1dae5d0, file "<stdin>", line 1>) 3 LOAD_CONST 2 ('<lambda>.<locals>.<listcomp>') 6 MAKE_FUNCTION 0 9 LOAD_GLOBAL 0 (range) 12 LOAD_CONST 3 (3) 15 CALL_FUNCTION 1 (1 positional, 0 keyword pair) 18 GET_ITER 19 CALL_FUNCTION 1 (1 positional, 0 keyword pair) 22 RETURN_VALUE Hence, the most logical way to handle conditions with 'as' clauses is to have them in the same scope. The special case for exceptions is because tracebacks would create refloops with the locals, and catching exceptions is extremely common. Nothing else needs that special case, so everything else can follow the 'with' block model and leave the name bound. ChrisA
- Previous message (by thread): [Python-ideas] If branch merging
- Next message (by thread): [Python-ideas] If branch merging
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]
More information about the Python-ideas mailing list