Python有两种错误:语法错误和异常。语法错误或者称之为解析错,在程序运行前的解析时就被发现,如果没有语法错误,就会解析完成,进入运行阶段,在运行期检测到的错误被称为异常。如果是函数名的括号后没有冒号,就属于语法错误,如果是除法中被除数写成0,就属于异常。
在很多python编辑器中,如果语法错,会有颜色提示,提醒大家改正,但是异常编辑器就无法发现,需要大家在编写时注意编码习惯,加上异常处理。当然现在我们有很多检查工具如Flake8、pylint等,来检查出哪些地方需要我们进行异常处理。如下我们介绍异常处理常见编码方法。
在异常处理时我们需要两个关键字:关键字try和关键字except。通常我们把我们的可能异常的代码放在try和except之间,示例代码如下。
import sys
try:
f = open('myfile.txt')
s = f.readline()
i = int(s.strip())
except OSError as err:
print("OS error: {0}".format(err))
except ValueError:
print("Could not convert data to an integer.")
except:
print("Unexpected error:", sys.exc_info()[0])
raise
在上述代码执行时,首先执行try子句即try和except之间的语句,如果没有异常发生,try子句执行后程序结束,except子句被忽略。如果在执行try子句的过程中发生了异常,那么try子句余下的部分将被忽略,进入异常的类型和 except 之后的名称相符的子句执行,如果发生的异常既不是OSError,也不是ValueError,则进入最后一个默认异常,将异常信息打印,并使用raise关键字将异常抛出。
大家仔细看下上面的代码,有问题吗?针对问题应该如何处理,此处请思考五分钟。
接着上面的例子,大家看出什么问题了吗?答案是文件没有正常被关闭。那么怎么优化该代码,我对代码的改进如下:
import sys
try:
f = open('myfile.txt')
s = f.readline()
i = int(s.strip())
except OSError as err:
print("OS error: {0}".format(err))
except ValueError:
print("Could not convert data to an integer.")
except:
print("Unexpected error:", sys.exc_info()[0])
raise
finally:
if not f.closed:
f.close()
我们添加了finally语句,无论exception是否被执行,finally内的语句一定会被执行。
针对资源类操作,Python提供了关键字with,不管在处理文件过程中是否发生异常,都能保证 with 语句执行完毕后已经关闭了打开的文件句柄。
使用with的示例代码如下:
import sys
try:
with open("myfile.txt") as f:
s = f.readline()
i = int(s.strip())
except OSError as err:
print("OS error: {0}".format(err))
except ValueError:
print("Could not convert data to an integer.")
except:
print("Unexpected error:", sys.exc_info()[0])
raise
用户自定义异常
我们可以通过创建一个新的异常类来拥有自己的异常。异常类继承自 Exception 类,可以直接继承,或者间接继承,自定义的异常类示例如下:
#myexception.py
class Error(Exception):
pass
class InputError(Error):
def __init__(self, message):
self.message = message
class TransitionError(Error):
def __init__(self, previous, next, message):
self.previous = previous
self.next = next
self.message = message
异常类的使用示例如下:
import myexception
while True:
try:
x = int(input("Please enter a number: "))
if 2 == x:
raise myexception.InputError("You can not input number 2, Please input another.")
else:
print("Your input is:", x)
continue
except ValueError:
print("This is no valid number. Please try again.")
示例打印如下:
如果你喜欢这篇文章,别忘了点赞和评论哦!