生成器和上下文管理器同时 [英] Generator and context manager at the same time
问题描述
想象一下,我有一些要运行的代码:
Imagine I have some code that I want it to run:
with F() as o:
while True:
a = o.send(2)
print(a)
这意味着 F
类应该返回一个 generator
,并且它也是 context manager
,通常我希望上下文管理器是生成器也是.
It means that the F
class should return an generator
and also it is context manager
, generally I want a context manager to be generator too.
我尝试过:
class F:
def __enter__(self):
return self
def __exit__(self, *exc):
print('exit')
def __next__(self):
return 5
def __iter__(self):
return self
按预期,这将返回 AttributeError:'F'对象没有属性'send'
,我通过添加以下内容来处理此错误:
As expected this will return AttributeError: 'F' object has no attribute 'send'
, I handled this error by adding:
def send(self, param):
self.__next__()
但是我认为这不是一个好方法,我环顾四周,找到 ,但是他们没有按照我的要求使用 send
,我需要该实例作为生成器.
but I think it is not a good way to do this, I look around and find this, but they are not using send
as I want, I need that instance to be a generator.
推荐答案
您可以使用 collections.abc
并从 Generator
继承类 F
>(手册页).如果您实现 enter 和 exit ,则您的实例将是生成器,并且还具有上下文管理器支持:
You can use collections.abc
and subclass your class F
from Generator
(manual pages). If you implement enter and exit, your instance will be generator and have context manager support as well:
from collections.abc import Generator
class F(Generator):
def __init__(self):
self.__my_generator = self._my_generator()
next(self.__my_generator) # prime the generator
def _my_generator(self):
while True:
v = yield 42
print('generator received ', v)
# context manager interace:
def __enter__(self):
return self
def __exit__(self, *exc):
print('exit')
# Generator interface:
def send(self, value):
return self.__my_generator.send(value)
def throw(self, typ, value=None, traceback=None):
return self.__my_generator.throw(typ, value, traceback)
with F() as o:
while True:
a = o.send(2)
print('I received ', a)
打印:
generator received 2
I received 42
...etc.
这篇关于生成器和上下文管理器同时的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!