在with语句表达式中引发的异常会发生什么?

ver*_*gil 8 python with-statement contextmanager

我对Python with声明的理解如下:

withstatement = with+ expression + as+ target + :+ suit

  1. 执行表达式并返回上下文管理器
  2. 上下文管理器__enter__返回一个目标值
  3. 套件已执行.
  4. __exit__调用上下文管理器的方法

我知道可以在step2和step3中处理异常,我的问题是如果在执行表达式的step1期间抛出异常,我可以获得上下文管理器吗?

如果不是,这是否意味着该with声明只是确保诉讼被正确执行和关闭?

就像with open("file") as f,如果文件不存在会发生什么?

Mar*_*ers 7

with语句仅管理步骤3中的异常.如果在步骤1(执行表达式)或步骤2(执行上下文管理器__enter__方法)中引发异常,则您没有(有效且可工作的)上下文管理器来处理异常.

因此,如果该文件不存在,则在步骤1中引发异常,并且上下文管理器无法处理该异常,因为从未创建该上下文管理器.

如果这是一个问题,您始终可以单独执行表达式部分:

try:
    context_manager = expression
except SomeSpecificException:
    # do something about the exception
else:
    with context_manager as target:
        # execute the suite
Run Code Online (Sandbox Code Playgroud)

如果在__enter__(步骤2)中引发异常,则尚未输入上下文,因此__exit__不会被调用.在该步骤处理异常的唯一选择是将整个with语句放在一个try...except块中.