有没有一种方法可以用with语句开始代码块,但是有条件地?
就像是:
if needs_with(): with get_stuff() as gs: # do nearly the same large block of stuff, # involving gs or not, depending on needs_with()
为了明确起见,一种情况将在with语句中包含一个块,而另一种可能性将是相同的块,但未包含(即,好像没有缩进)
当然,最初的实验会产生压痕错误。
如果要避免重复代码,并使用3.7(contextlib.nullcontext引入时)甚至3.3(引入时)之前的Python版本contextlib.ExitStack,则可以执行以下操作:
contextlib.nullcontext
contextlib.ExitStack
class dummy_context_mgr(): def __enter__(self): return None def __exit__(self, exc_type, exc_value, traceback): return False
要么:
import contextlib @contextlib.contextmanager def dummy_context_mgr(): yield None
然后将其用作:
with get_stuff() if needs_with() else dummy_context_mgr() as gs: # do stuff involving gs or not
您也可以根据get_stuff()返回不同的值needs_with()。
get_stuff()
needs_with()
(有关在以后的版本中可以做什么的信息,请参阅Mike的答案
从Python 3.7开始,您可以使用contextlib.nullcontext:
from contextlib import nullcontext if needs_with(): cm = get_stuff() else: cm = nullcontext() with cm as gs: # Do stuff
contextlib.nullcontext几乎只是一个无操作上下文管理器。如果您依赖在as:之后存在的内容,则可以为其传递一个将产生的参数:
>>> with nullcontext(5) as value: ... print(value) ... 5
否则它将返回None:
>>> with nullcontext() as value: ... print(value) ... None
超级整洁,请在此处查看文档:https : //docs.python.org/3/library/contextlib.html#contextlib.nullcontext