仅在引发异常时清理对象

plo*_*lok 3 python exception try-catch-finally

如果不是所有必须在其上完成的操作都成功(即,如果引发异常),我需要删除一个文件.它可以像使用一样简单,除了:,删除文件然后重新引发异常,但是在这种情况下,如果由于任何神秘的原因无法在except子句中删除文件,原始异常将会丢失.

我能想到的最好的是:

try:
    file_path = "whatever.jpg"
    # do stuff with file
except:
    exception_raised = True
    raise
finally:
    try:
        if exception_raised:
            os.unlink(file_path)
    except:
        pass

return file_path   # everything OK
Run Code Online (Sandbox Code Playgroud)

有人知道更好,更Pythonic的方法吗?

Sve*_*ach 5

另一种选择是如果您不想丢失它,只需存储异常:

Python 3.x版本:

try:
    file_path = "whatever.jpg"
    # do stuff with file
except BaseException as e:
    try:
        os.unlink(file_path)
    except Exception:
        traceback.print_exc()
    raise e
Run Code Online (Sandbox Code Playgroud)

Python 2.x版本稍微复杂一些,因为您需要手动存储完整的异常信息(否则您将丢失回溯):

try:
    file_path = "whatever.jpg"
    # do stuff with file
except:
    e = sys.exc_info()
    try:
        os.unlink(file_path)
    except Exception:
        traceback.print_exc()
    raise e[0], e[1], e[2]
Run Code Online (Sandbox Code Playgroud)

编辑:只捕获Exception内部try块中的子类,因为您不想捕获SystemExitKeyboardInterrupt在此处.同时报告在取消链接期间发生的任何重复,而不是仅丢弃它.