Python 装饰器 Try/Except 不引发错误
Python Decorator With Try/Except Not Raising Error
我正在试验 Python 装饰器以了解它发生了什么,我遇到了一个令人头疼的问题。
我的代码是这样的(python 2.7.6):
import traceback
def dec(func):
def wrapped(*args, **kwargs):
try:
if flag:
print 'flagged'
else:
print 'unflagged'
except NameError as e:
print 'error?'
raise
finally:
return func(*args, **kwargs)
return wrapped
@dec
def foo(x):
print x
foo(3)
当运行时,输出为:
error?
3
我预计调用 foo(3) 会引发:
NameError: global name 'flag' is not defined
为什么 "raise" 没有加注?显然,错误已被捕获 - Except 块中的打印已执行...
finally
中的 return
覆盖并取消任何可能触发 finally
块的异常或函数 return。这记录在 Python Language Reference:
If finally
is present, it specifies a ‘cleanup’ handler. The try
clause is executed, including any except
and else
clauses. If an
exception occurs in any of the clauses and is not handled, the
exception is temporarily saved. The finally
clause is executed. If
there is a saved exception, it is re-raised at the end of the
finally
clause. If the finally
clause raises another exception or
executes a return
or break
statement, the saved exception is
discarded:
例如:
def f():
try:
1/0
finally:
return
f() # No exception
def g():
try:
return 1
finally:
return 0
g() # 0
def h():
try:
raise NameError
finally:
raise TypeError
h() # TypeError
我正在试验 Python 装饰器以了解它发生了什么,我遇到了一个令人头疼的问题。
我的代码是这样的(python 2.7.6):
import traceback
def dec(func):
def wrapped(*args, **kwargs):
try:
if flag:
print 'flagged'
else:
print 'unflagged'
except NameError as e:
print 'error?'
raise
finally:
return func(*args, **kwargs)
return wrapped
@dec
def foo(x):
print x
foo(3)
当运行时,输出为:
error?
3
我预计调用 foo(3) 会引发:
NameError: global name 'flag' is not defined
为什么 "raise" 没有加注?显然,错误已被捕获 - Except 块中的打印已执行...
finally
中的 return
覆盖并取消任何可能触发 finally
块的异常或函数 return。这记录在 Python Language Reference:
If
finally
is present, it specifies a ‘cleanup’ handler. Thetry
clause is executed, including anyexcept
andelse
clauses. If an exception occurs in any of the clauses and is not handled, the exception is temporarily saved. Thefinally
clause is executed. If there is a saved exception, it is re-raised at the end of thefinally
clause. If thefinally
clause raises another exception or executes areturn
orbreak
statement, the saved exception is discarded:
例如:
def f():
try:
1/0
finally:
return
f() # No exception
def g():
try:
return 1
finally:
return 0
g() # 0
def h():
try:
raise NameError
finally:
raise TypeError
h() # TypeError