is a decorator in python exactly the same as calling a function on a function?
I thought that doing
@f
def g():
print 'hello'
is exactly the same as
def g():
print 'hello'
g=f(g)
But, I had this code, that uses contextlib.contextmanager:
@contextlib.contextmanager
def f():
print 1
yield
print 2
with f:
print 3
which works and yields 1开发者_运维技巧 3 2
And when I tried to change it into
def f():
print 1
yield
print 2
f=contextlib.contextmanager(f)
with f:
print 3
I get AttributeError: 'function' object has no attribute '__exit__'
What am I missing? is there some black magic specifically in contextlib.contextmanager, or do i misunderstand how decorators work in general?
Yes, decorator is exactly same as calling a function and assigning to returned value
In this case error comes because you are not calling function, so correct code would be
def f():
print 1
yield
print 2
f=contextlib.contextmanager(f)
with f():
print 3
also I am not sure if you tested code, because decorator code you have given will fail due to same reason
@contextlib.contextmanager
def f():
print 1
yield
print 2
with f:
print 3
Error:
with f:
AttributeError: 'function' object has no attribute '__exit__'
精彩评论