Python:将try-except用作表达式?
我发现自己总是遇到这样的情况:
variable = ""
try:
variable = ... do some file loading stuff ...
except:
variable = ""
有没有办法把这个简化成一个表达式?就像用if-else语句,你可以把:
variable = ""
if something:
variable = somethingelse
else:
variable = ""
变成
variable = somethingelse if something else ""
有没有类似的方式可以用在try-catch上呢?
8 个回答
16
这里有一个上下文管理器,它提供了一个小小的快捷方式:
from contextlib import contextmanager
@contextmanager
def catch(*exceptions, **kwargs):
try:
yield kwargs.get("default", None)
except exceptions or Exception:
pass
使用方法:
with catch(ZeroDivisionError, default=0) as x:
x = 3 / 0 # error
print x # prints 0, the default
这个上下文管理器的基本思路是,它会返回你传入的默认值,然后这个值会被赋给你在with
语句的as
部分指定的变量。在这个上下文中,你可以执行一个尝试给同一个变量赋值的语句。如果这个赋值过程中出现了错误,它会被上下文管理器捕获并悄悄忽略,但因为赋值没有成功,所以默认值依然保留。
这个方法特别适合那些虽然需要多行计算,但最终结果却只有一个值的情况。
20
def try_except(success, failure):
try:
return success()
except:
return failure()
variable = try_except(do_some_file_loading_stuff, lambda: '')
我觉得这段代码自己就能说明问题。它会返回success
的值,除非出现错误,这时它会返回failure
的值。如果do_some_file_loading_stuff
是一个表达式,而不仅仅是一个函数调用,那就把它放在lambda
里。
编辑:@kindall和我稍微改进了一下他的版本,现在和我的一样快,如果你想的话调用方式完全相同,还有更多功能,而且行数也一样。快去用吧!
def try_except(success, failure, *exceptions):
try:
return success()
except exceptions or Exception:
return failure() if callable(failure) else failure
29
因为agf已经提供了我推荐的方法,这里是他的方法版本,做了一些小改进:
def try_except(success, failure, *exceptions):
try:
return success()
except exceptions or Exception:
return failure() if callable(failure) else failure
这个版本:
让你可以指定具体要捕获哪些异常,作为额外的可选参数。你应该尽量只捕获最少的异常,这样可以处理问题,而那些你无法处理的异常就让它们向上传递给调用者。
支持使用普通值和函数作为失败值。这可以让你在很多情况下不必使用lambda表达式。(当然,你可以直接用
str
代替lambda: ''
。)