Add some more to the rationale section in PEP 377

This commit is contained in:
Nick Coghlan 2009-03-14 07:28:35 +00:00
parent 2d3b72243a
commit 01ddf563f6
1 changed files with 87 additions and 29 deletions

View File

@ -164,6 +164,61 @@ then handles and suppresses::
suppress = self.cmA.__exit__(*args): suppress = self.cmA.__exit__(*args):
return suppress return suppress
With the proposed semantic change in place, the contextlib based examples
above would then "just work", but the class based version would need
adjustment to take advantage of the new semantics::
class CM(object):
def __init__(self):
self.cmA = None
self.cmB = None
def __enter__(self):
if self.cmA is not None:
raise RuntimeError("Can't re-use this CM")
self.cmA = cmA()
self.cmA.__enter__()
try:
self.cmB = cmB()
self.cmB.__enter__()
except:
if self.cmA.__exit__(*sys.exc_info()):
# Suppress the exception, but don't run
# the body of the with statement either
raise SkipStatement
raise
def __exit__(self, *args):
suppress = False
try:
if self.cmB is not None:
suppress = self.cmB.__exit__(*args)
except:
suppress = self.cmA.__exit__(*sys.exc_info()):
if not suppress:
# Exception has changed, so reraise explicitly
raise
else:
if suppress:
# cmB already suppressed the exception,
# so don't pass it to cmA
suppress = self.cmA.__exit__(None, None, None):
else:
suppress = self.cmA.__exit__(*args):
return suppress
There is currently a tentative suggestion [3] to add import-style syntax to
the ``with`` statement to allow multiple context managers to be included in
a single ``with`` statement without needing to use ``contextlib.nested``. In
that case the compiler has the option of simply emitting multiple ``with``
statements at the AST level, thus allowing the semantics of actual nested
``with`` statements to be reproduced accurately. However, such a change
would highlight rather than alleviate the problem the current PEP aims to
address: it would not be possible to use ``contextlib.contextmanager``to
reliably factor out such ``with`` statements, as they would exhibit exactly
the same semantic differences as are seen with the ``combined()`` context
manager in the above example.
Reference Implementation Reference Implementation
======================== ========================
@ -186,6 +241,9 @@ References
.. [2] PEP 343: The "with" Statement .. [2] PEP 343: The "with" Statement
(http://www.python.org/dev/peps/pep-0343/) (http://www.python.org/dev/peps/pep-0343/)
.. [3] Import-style syntax to reduce indentation of nested with statements
(http://mail.python.org/pipermail/python-ideas/2009-March/003188.html)
Copyright Copyright
========= =========