Python的"open()"会为"找不到文件"抛出不同的错误 - 如何处理这两个异常?

42 python filenotfoundexception ioerror python-3.x

我有一个脚本,提示用户输入文件名(要打开的文件),如果当前目录中不存在该文件,则再次提示用户.这是简短的版本:

file = input("Type filename: ")

...
try:
    fileContent = open(filename, "r")
    ...
except FileNotFoundError:
    ...
Run Code Online (Sandbox Code Playgroud)

当我在Python 3.3x中使用我的MacOS X测试我的脚本时,当我故意键入错误的文件名时它完全正常(它在"expect"下执行套件).

但是,当我想在Python 3.2x中的Windows计算机上运行我的代码时,我收到一条错误,指出未定义"FileNotFoundError".因此,Windows上的Python 3.2认为"FileNotFoundError"是一个变量,程序退出并出现错误.

我发现如果输入文件名无效,Windows上的Python 3.2会抛出"IOError".我在我的Linux机器上用Python 2.7测试过,它也是一个IOError.

我现在的问题是,代码用

except "FileNotFoundError":
Run Code Online (Sandbox Code Playgroud)

将无法在Windows的Python 3.2上运行,但如果我将其更改为

except "IOError":
Run Code Online (Sandbox Code Playgroud)

它不再适用于我的Mac.

我怎么能解决它?我能想到的唯一方法是使用just except,我通常不想要.

Rus*_*ove 65

在3.3中,IOError成为别名OSError,并且FileNotFoundError是其子类OSError.所以你可能会尝试

except (OSError, IOError) as e:
   ...
Run Code Online (Sandbox Code Playgroud)

这将构建一个相当广泛的网络,你不能假设没有检查的例外是"找不到文件" e.errno,但它可能涵盖你的用例.

PEP 3151讨论了细节变化的基本原理.


cwa*_*ole 10

这对我来说比简单更好except:,但我不确定它是否是最好的解决方案:

error_to_catch = getattr(__builtins__,'FileNotFoundError', IOError)

try:
    f = open('.....')
except error_to_catch:
    print('!')
Run Code Online (Sandbox Code Playgroud)


Ale*_*Che 6

因此,仅在找不到文件时才完全捕获,我这样做:

import errno
try:
   open(filename, 'r')
except (OSError, IOError) as e: # FileNotFoundError does not exist on Python < 3.3
   if getattr(e, 'errno', 0) == errno.ENOENT:
      ... # file not found
   raise
Run Code Online (Sandbox Code Playgroud)