gpt4 book ai didi

python - 上下文管理器严格适用于生成器吗?

转载 作者:太空宇宙 更新时间:2023-11-03 18:17:34 25 4
gpt4 key购买 nike

Python 的 with exp() as obj: 语法对于任何具有“强制”进入和退出方法的对象都很有吸引力 - 考虑到人们尝试扩展 obj.__del__ 的情况由于结果不佳等等,这似乎表明人们应该使用 __enter__ 和 __exit__ 方法来代替。

我首先想到的是有进入和退出方法的状态机;无论如何,这是基本要处理的事情,但使状态机的实际实现非常简单。

class State(object):
def __init__(self, strategy):
self.strategy = strategy

def __enter__(self, *args):
return self

def __call__(self, *args, **kwargs):
self.strategy(self, *args, **kwargs)

def __exit__(self, *args):
clean_up_things()

...
...
...
def state_handle():
states = (State(foo), State(bar), State(eggs))
for state in states:
with state() as s:
what_ever(s)

然而,人们通常将 with XXX as YYY 语法视为 try/finally 子句和/或 yield 语句的替代,我不断发现的一件事是,Python 社区喜欢知道当某个功能实现时会发生什么。因此,如果使用错误的咒语来解决正确的问题,它仍然是错误的答案。

Python 是否出于某种特定原因故意为生成器保留 with...as 语法,或者可以按照自己认为合适的方式应用此语法? 如果有目的,那目的是什么? (我在 PEP 8 中几乎没有看到 with/as ,如果那是正确的地方的话)

最佳答案

您似乎误解了某些内容。

[I]t seems that one typically sees with XXX as YYY syntax as a replacement for try/finally clauses and/or yield statements

不,没有人。每当您需要管理上下文时,都可以使用上下文管理器。您的用例很好。

使用上下文管理器来替换 try ..finally use 是一个用例。我不确定你从哪里得到关于发电机的想法;也许是因为有帮助 @contextlib.contextmanager() decorator让您可以将生成器转变为上下文管理器,从而简化上下文管理器的创建。

我至少能想到Python标准库中的两个反例:

  • unittest ;使用 assertRaises 作为上下文管理器,您可以断言引发异常,然后测试异常的各个方面。

  • decimal ; localcontext 管理十进制数精度、舍入和其他方面。

这些不能替代 try ..finally处理程序,尽管您可以想象为 decimal 获得相同的功能上下文为 try ..finally以及添加的线程安全层;然而,这将需要更多的工作。

您可能会对原始的 Python 增强提案感兴趣:http://www.python.org/dev/peps/pep-0343/

关于python - 上下文管理器严格适用于生成器吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24764834/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com