了解 python3 嵌套上下文管理器
Understand python3 nested context managers
我有一个 class:
class OuterCtxManager:
def __enter__(self):
print('Outer enter')
def __exit__(self, exc_type, exc_val, exc_tb):
print('Outer exit')
当我这样做时:
def test_func():
return OuterCtxManager()
with test_func() as context_manager:
print('context_manager')
它打印:
Outer enter
context_manager
Outer exit
尽管在函数中对已创建的对象使用了上下文管理器,为什么它仍然打印 Outer enter
和 Outer exit
? (而不是像 with OuterCtxManager() as ocm
这样创建对象时直接使用)
接下来是有趣的事情:
当我这样做时:
def test_func():
first_object = OuterCtxManager()
second_object = OuterCtxManager()
return [first_object, second_object]
with test_func() as context_manager:
print('context_manager')
它提高了:
AttributeError: enter
最后,当我这样做时:
class OuterCtxManager:
def __init__(self):
self.inner_ctx = InnerCtxManager()
def __enter__(self):
print('Outer enter')
def __exit__(self, exc_type, exc_val, exc_tb):
print('Outer exit')
class InnerCtxManager:
def __init__(self):
print('inner_created')
def __enter__(self):
print('Inner enter')
def __exit__(self, exc_type, exc_val, exc_tb):
print('Inner exit')
def test_func():
first_object = OuterCtxManager()
return first_object
with test_func() as context_manager:
print('context_manager')
它打印:
inner_created
Outer enter
context_manager
Outer exit
我没有收到任何错误。我也没有得到 Inner created
和 Inner enter
。为什么?
Why does it print Outer enter and Outer exit at all despite using context manager on already created object in a function?
你定义的with
语句说python应该在with
语句的内容执行前调用__enter__
,然后调用__exit__
。
对象是否已经初始化并不重要。 with 语句无论如何都会调用 __enter__
和 __exit__
It raises AttributeError: enter
当您返回一个元组并且该元组不包含 __enter__
的定义时,将引发此错误。
I don't get any errors. Neither I get Inner created and Inner enter. Why is that so?
您没有收到任何错误,因为您在 OuterCtxManager
中正确使用了 with
语句,并且没有得到输出 Inner enter
和 Inner exit
,因为您没有在 InnerCtxManager
类型上使用 with
语句。
我有一个 class:
class OuterCtxManager:
def __enter__(self):
print('Outer enter')
def __exit__(self, exc_type, exc_val, exc_tb):
print('Outer exit')
当我这样做时:
def test_func():
return OuterCtxManager()
with test_func() as context_manager:
print('context_manager')
它打印:
Outer enter
context_manager
Outer exit
尽管在函数中对已创建的对象使用了上下文管理器,为什么它仍然打印 Outer enter
和 Outer exit
? (而不是像 with OuterCtxManager() as ocm
这样创建对象时直接使用)
接下来是有趣的事情:
当我这样做时:
def test_func():
first_object = OuterCtxManager()
second_object = OuterCtxManager()
return [first_object, second_object]
with test_func() as context_manager:
print('context_manager')
它提高了:
AttributeError: enter
最后,当我这样做时:
class OuterCtxManager:
def __init__(self):
self.inner_ctx = InnerCtxManager()
def __enter__(self):
print('Outer enter')
def __exit__(self, exc_type, exc_val, exc_tb):
print('Outer exit')
class InnerCtxManager:
def __init__(self):
print('inner_created')
def __enter__(self):
print('Inner enter')
def __exit__(self, exc_type, exc_val, exc_tb):
print('Inner exit')
def test_func():
first_object = OuterCtxManager()
return first_object
with test_func() as context_manager:
print('context_manager')
它打印:
inner_created
Outer enter
context_manager
Outer exit
我没有收到任何错误。我也没有得到 Inner created
和 Inner enter
。为什么?
Why does it print Outer enter and Outer exit at all despite using context manager on already created object in a function?
你定义的with
语句说python应该在with
语句的内容执行前调用__enter__
,然后调用__exit__
。
对象是否已经初始化并不重要。 with 语句无论如何都会调用 __enter__
和 __exit__
It raises
AttributeError: enter
当您返回一个元组并且该元组不包含 __enter__
的定义时,将引发此错误。
I don't get any errors. Neither I get Inner created and Inner enter. Why is that so?
您没有收到任何错误,因为您在 OuterCtxManager
中正确使用了 with
语句,并且没有得到输出 Inner enter
和 Inner exit
,因为您没有在 InnerCtxManager
类型上使用 with
语句。