我们都知道在学习C语言或者Java中,编译器可以捕获很多语法错误,但是在Python中,只有在程序运行后才会执行语法检查。所以,只有在运行或测试程序时,才会真正知道该程序能不能正常运行,因此,掌握一定的异常处理语句和程序调试方法是十分必要的。
①了解什么是异常
②掌握如何使用try…execpt语句捕获异常
③掌握try…execpt…else语句的应用
④掌握try…execpt…finally语句的应用
⑤掌握如何使用raise语句抛出的异常
⑥掌握如何使用自带的IDLE进行程序调试
⑦掌握如何使用assert语句调试程序
在程序运行的时候经常出现各种各样的错误,但这些错误是可以容易发现,并且能够避免的,但是,有一些程序是隐藏的,通常和操作者的操作有关。
例1.模拟幼儿园分苹果;
def division():
'''功能:分苹果'''
print("\n===================== 分苹果了 =====================\n")
apple = int(input("请输入苹果的个数:")) # 输入苹果的个数
children = int(input("请输入来了几个小朋友:"))
result = apple//children # 计算每人分几个苹果
remain =apple-result*children # 计算余下几个苹果
if remain>0:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,
"个,剩下",remain,"个。")
else:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,"个。")
if __name__ == '__main__':
division() # 调用分苹果的函数
运行程序,当输入的苹果和小朋友的个数都为10时,显示如下;
如果输入有十个苹果,但不小心输入的小朋友是0个,将得到以下错误;
如下表所示,Python中常见的异常
异常 | 描述 |
---|---|
NameError | 尝试访问一个没有声明的变量引发的错误 |
IndexError | 索引超出序列范围引发的错误 |
IndentationError | 缩进错误 |
ValueError | 传入的值错误 |
KeyError | 请求一个不存在的字典关键字引发的错误 |
IOError | 输入输出错误 |
ImportError | 当import语句无法找到模块或form无法在模块中找到相应的名称 |
AttributeError | 尝试访问未知的对象属性引发的错误 |
TypeError | 类型不适合引发的错误 |
MemoryError | 内存不足 |
ZeroDivisionError | 除数为0引发的错误 |
在程序开发的时候,有些错误并不是每次都会出现,程序员需要认真对待,才能更好的避免错误。
2.1 try…except语句
在Python中,提供了try…except语句捕获并处理异常,在使用时,把可能产生错误的代码放在try语句块中,把处理结果放在except语句块中,这样,当try语句块中的代码出现错误,就会执行except语句块中的代码,如果try语句块中的代码没有错误,那么except语句块将不会执行,具体语法如下:
try:
block1
except [ExceptionName [as alias]]:
block2
例2.模拟幼儿园分苹果;
def division():
'''功能:分苹果'''
print("\n===================== 分苹果了 =====================\n")
apple = int(input("请输入苹果的个数:")) # 输入苹果的个数
children = int(input("请输入来了几个小朋友:"))
result = apple//children # 计算每人分几个苹果
remain =apple-result*children # 计算余下几个苹果
if remain>0:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,
"个,剩下",remain,"个。")
else:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,"个。")
if __name__ == '__main__':
try: # 捕获异常
division() # 调用分苹果的函数
except ZeroDivisionError: # 处理异常
print("\n出错了 ~_~ ——苹果不能被0个小朋友分!")
当输入苹果个数为10,小朋友个数为0时,程序不抛出错误,运行结果如下所示;
但是上面的程序,苹果数和小朋友个数为整数,当出现小数时,同样也会抛出错误;
出现小数错误时,可以在程序的后面添加如下代码,则可以不抛出错误;
except ValueError as e: # 处理ValueError异常
print("输入错误:",e) # 输出错误原因
2.2 try…except…else语句
try…except…else语句就是在原来的 try…except语句上再增加else语句,用于指定当try语句块中没有发现异常时要执行的语句块,该语句块中的内容当try语句中发现异常时,将不被执行,例如:
def division():
'''功能:分苹果'''
print("\n===================== 分苹果了 =====================\n")
apple = int(input("请输入苹果的个数:")) # 输入苹果的个数
children = int(input("请输入来了几个小朋友:"))
result = apple//children # 计算每人分几个苹果
remain =apple-result*children # 计算余下几个苹果
if remain>0:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,
"个,剩下",remain,"个。")
else:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,"个。")
if __name__ == '__main__':
try: # 捕获异常
division() # 调用分苹果的函数
except ZeroDivisionError: # 处理异常
print("\n出错了 ~_~ ——苹果不能被0个小朋友分!")
except ValueError as e: # 处理ValueError异常
print("输入错误:",e) # 输出错误原因
else:
print("分苹果顺利完成")
运行结果为:
2.3 try…except…finally语句
完整的异常处理语句应该包含finally代码块,通常情况之下,无论程序中有无异常产生,finally代码块的代码都会被执行,其基本格式如下;
try:
block1
except [ExceptionName [as alias]]:
block2
finally:
block3
例如:当小朋友的个数为0时;
def division():
'''功能:分苹果'''
print("\n===================== 分苹果了 =====================\n")
apple = int(input("请输入苹果的个数:")) # 输入苹果的个数
children = int(input("请输入来了几个小朋友:"))
result = apple//children # 计算每人分几个苹果
remain =apple-result*children # 计算余下几个苹果
if remain>0:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,
"个,剩下",remain,"个。")
else:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,"个。")
if __name__ == '__main__':
try: # 捕获异常
division() # 调用分苹果的函数
except ZeroDivisionError: # 处理异常
print("\n出错了 ~_~ ——苹果不能被0个小朋友分!")
except ValueError as e: # 处理ValueError异常
print("输入错误:",e) # 输出错误原因
else:
print("分苹果顺利完成")
finally:
print("进行一次分苹果操作。")
运行结果为:
2.4 使用raise语句抛出异常
如果某个函数或方法可能会产生异常,但不想在当前函数或者方法中处理这个问题,则可以使用raise语句在函数或方法中抛出异常,格式为
raise []ExceptionName[(reason)]
例如:模拟幼儿园分苹果(每个人至少分到一个苹果)。
def division():
'''功能:分苹果'''
print("\n===================== 分苹果了 =====================\n")
apple = int(input("请输入苹果的个数:")) # 输入苹果的个数
children = int(input("请输入来了几个小朋友:"))
if apple < children:
raise ValueError("苹果太少了,不够分...")
result = apple // children # 计算每人分几个苹果
remain = apple - result * children # 计算余下几个苹果
if remain > 0:
print(apple, "个苹果,平均分给", children, "个小朋友,每人分", result,
"个,剩下", remain, "个。")
else:
print(apple, "个苹果,平均分给", children, "个小朋友,每人分", result, "个。")
if __name__ == '__main__':
try: # 捕获异常
division() # 调用分苹果的函数
except ZeroDivisionError: # 处理异常
print("\n出错了 ~_~ ——苹果不能被0个小朋友分!")
except ValueError as e:
print("\n出错了 ~_~ ——",e)
在程序开发的时候,避免不了一些错误,有语法方面的,也有逻辑方面的,对于语法方面的错误容易检测,因为程序会直接停止,并且给出错误提示,相对而言逻辑错误就 不太好找出错误,所以一定要掌握一定的程序调试方法,
3.1 利用自带的IDLE进行程序调试
(1)打开IDLE,在主菜单中选择Debug→Debugger;
(2)打开需要调试的文件,并且添加新的断点,
3.2 使用assert语句调试程序
在程序开发中,除了使用开发工具自带的程序调试工具之外,还可以在代码中通过print()函数把可能出现的问题的变量输出进行查看,但是这种方法会产生很多垃圾,所以调试之后还需要进行删除,语法格式为:
assert expression [,reason]
例如:
def division():
'''功能:分苹果'''
print("\n===================== 分苹果了 =====================\n")
apple = int(input("请输入苹果的个数:")) # 输入苹果的个数
children = int(input("请输入来了几个小朋友:"))
assert apple > children ,"苹果不够分"
result = apple//children # 计算每人分几个苹果
remain =apple-result*children # 计算余下几个苹果
if remain>0:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,
"个,剩下",remain,"个。")
else:
print(apple,"个苹果,平均分给",children,"个小朋友,每人分",result,"个。")
if __name__ == '__main__':
division() # 调用分苹果的函数
运行结果为:
程序抛出错误,可以将 division() 替换为如下语句,程序就可以避免出现错误,
try:
division() # 调用分苹果的函数
except AssertionError as e:
print("\n输入有误:",e)