零基础入门学Python系列内容的学习目录 → \rightarrow →零基础入门学Python系列内容汇总。
需要学习的基础知识有:异常处理、 try-except语句、try-finally语句、raise语句、else语句、with语句等。
1. 一些异常什么是异常呢?举个例子:
file_name = input('请输入要打开的文件名:')
f = open(file_name, 'r')
print('文件的内容是:')
for each_line in f:
print(each_line)
对于上面的这段程序,如果用户输入一个不存在的文件名,那么就会报错,抛出一个FileNotFoundError
异常。
>>>
请输入要打开的文件名:python
Traceback (most recent call last):
File “C:/Users/123/Desktop/1.py”, line 2, in < module >
f = open(file_name, ‘r’)
FileNotFoundError: [Errno 2] No such file or directory: ‘python’
下面列举一些异常。
-
1. AssertionError:断言语句(assert)失败
当assert
这个关键字后边的条件为假的时候,程序将停止并抛出AssertionError
异常。assert
语句一般是在测试程序的时候用于在代码中置入检查点:
example1:>>> my_list = [“python”]
>>> assert len(my_list) > 0
>>> my_list.pop()
‘python’
>>> assert len(my_list) > 0
Traceback (most recent call last):
File “<pyshell#4>”, line 1, in < module >
assert len(my_list) > 0
AssertionError -
2. AttributeError:尝试访问未知的对象属性
当试图访问的对象属性不存在时抛出的异常:
example2:>>> my_list = [ ]
>>> my_list.python
Traceback (most recent call last):
File “<pyshell#6>”, line 1, in < module >
my_list.python
AttributeError: ‘list’ object has no attribute ‘python’ -
3. IndexError:索引超出序列的范围
在使用序列的时候就常常会遇到IndexError
异常,原因是索引超出序列范围的内容:
example3:>>> my_list =[1, 2, 3]
>>> my_list[3]
Traceback (most recent call last):
File “<pyshell#8>”, line 1, in < module >
my_list[3]
IndexError: list index out of range -
4. KeyError:字典中查找一个不存在的关键字
当试图在字典中查找一个不存在的关键字时就会引发KeyError
异常,因此建议使用dict.get()
方法:
example4:>>> my_dict = {“one”:1, “two”:2, “three”:3}
>>> my_dict[“one”]
1
>>> my_dict[“four”]
Traceback (most recent call last):
File “<pyshell#11>”, line 1, in < module >
my_dict[“four”]
KeyError: ‘four’ -
5. NameError:尝试访问一个不存在的变量
当尝试访问一个不存在的变量时,Python会抛出NameError
异常:
example5:>>> python
Traceback (most recent call last):
File “<pyshell#12>”, line 1, in < module >
python
NameError: name ‘python’ is not defined -
6. OSError:操作系统产生的异常
OSError
顾名思义就是操作系统产生的异常,像打开一个不存在的文件会引发FileNotFoundError
,而这个FileNotFoundError
就是OSError
的子类。 -
7. SyntaxError:Python的语法错误
如果遇到Syntaxtrror
是Python的语法错误,这时Python的代码并不能继续执行,你应该先找到并改正错误:
example6:>>> print “Hello, python!”
SyntaxError: Missing parentheses in call to ‘print’ -
8. TypeError:不同类型间的无效操作
有些类型不同是不能相互进行计算的,否则会抛出TypeError
异常:
example7:>>> 1 + “1”
Traceback (most recent call last):
File “<pyshell#16>”, line 1, in < module >
1 + “1”
TypeError: unsupported operand type(s) for +: ‘int’ and ‘str’ -
9. ZeroDivisionError:除数为零
除数为零就会引发ZeroDivisionError
异常:
example8:>>> 5 / 0
Traceback (most recent call last):
File “<pyshell#17>”, line 1, in < module >
5 / 0
ZeroDivisionError: division by zero
如果程序抛出异常就说明这个程序有问题,我们可以通过捕获这些异常去纠正这些错误。那应该如何捕获和处理异常呢?
异常捕获可以使用try
语句来实现,任何出现在try
语句范围内的异常都会被及时捕获到。try
语句有两种实现形式:一种是try-except
另一种是try-finally
。
try-except
语句格式如下:
try:
检测范围
except Exception [as reason]:
出现异常(Exception)后的处理代码
try-except
语句用于检测和处理异常。
看一个例子:
f = open('文档.txt')
print(f.read())
f.close()
以上代码在“文档.txt”这个文档不存在的时候,Python就会报错说文件不存在:
>>>
Traceback (most recent call last):
File “<pyshell#19>”, line 1, in < module >
f = open(‘文档.txt’)
FileNotFoundError: [Errno 2] No such file or directory: ‘文档.txt’
>>>
显然这样的用户体验不好,因此可以这么修改:
try:
f = open('文档.txt')
print(f.read())
f.close()
except OSError:
print('文件打开的过程中出错了!')
>>>
文件打开的过程中出错了!
>>>
但是从程序员的角度来看,导致OSError
异常的原因有很多(例如FileExistsError
、FileNotFoundError
、PermissionError
等等),所以想要直到错误的具体内容,可以用as
把具体的错误信息给打印出来:
try:
f = open('文档.txt')
print(f.read())
f.close()
except OSError as reason:
print('文件出错了! \n错误原因是:' + str(reason))
>>>
文件出错了!
错误原因是:[Errno 2] No such file or directory: ‘文档.txt’
>>>
2.1 针对不同异常设置多个except
一个try
语句还可以和多个except
语句搭配,分别对感兴趣的异常进行检测处理:
try:
sum = 1 + '1'
f = open('文档.txt')
print(f.read())
f.close()
except OSError as reason:
print('文件出错了! \n错误原因是:' + str(reason))
except TypeError as reason:
print('类型出错了! \n错误原因是:' + str(reason))
>>>
类型出错了!
错误原因是:unsupported operand type(s) for +: ‘int’ and ‘str’
>>>
2.2 对多个异常统一处理
except后边还可以跟多个异常,然后对这些异常进行统一的处理:
try:
int('abc')
sum = 1 + '1'
f = open('文档.txt')
print(f.read())
f.close()
except (OSError, TypeError) as reason:
print('文件出错了! \n错误原因是:' + str(reason))
2.3 捕获所有异常
如果我们无法确定要对哪一类异常进行处理,只是希望在try
语句块里一旦出现任何异常,可以给用户一个“看得懂”的提醒,那么可以这么做:
...
except (OSError, TypeError) as reason:
print('出错啦~')
...
不过通常不建议这么做,因为它会隐藏所有程序员未想到并且未做好处理准备的错误,例如当用户输入Ctrl+C
试图终止程序,却被解释为KeyboardInterrupt
异常。另外要注意的是,try
语句检测范围内一旦出现异常,剩下的语句将不会被执行。
如果“文档.txt”确实存在,open()
函数正常返回文件对象,但异常却发生在成功打开文件后的sum=1 + '1'
语句上。此时Python将直接跳到except
语句,也就是说,文件打开了,但并没有执行关闭文件的命令:
try:
f = open('文档.txt')
print(f.read())
sum = 1 + '1'
f.close()
except:
print('出错了!')
为了实现像这种“就算出现异常,但也不得不执行的收尾工作(比如在程序崩溃前保存用户文档)”,引入了finally
来扩展try
:
try:
f = open('文档.txt')
print(f.read())
sum = 1 + '1'
except:
print('出错了!')
finally:
f.close()
如果try
语句块中没有出现任何运行时错误,会跳except
语句块执行finally
语句块内容。如果出现异常,则会先执行except
语句块的内容再执行finally
语句块的内容。总之finally
语句块中的内容就是确保无论如何都将被执行的内容。
可以使用raise
语句让代码自己抛出一个异常:
>>> raise ZeroDivisionError
Traceback (most recent call last):
File “<pyshell#0>”, line 1, in < module >
raise ZeroDivisionError
ZeroDivisionError
抛出的异常还可以带参数,表示异常的解释:
>>>raise ZeroDivisionError(“除数不能为零!”)
Traceback(most recent call last):
File"<pyshell#2>",1ine 1,in< module >
raise ZeroDivisionError(“除数不能为零!”)
ZeroDivisionError:除数不能为零!
在Python中,else
语句不仅能跟if
语句搭,构成“要么怎样,要么不怎样”的句式;它还能跟循环语句(for
语句或者while
语句),构成“干完了能怎样,干不完就别想怎样”的句式;其实else
语句还能够跟刚刚的异常处理进行搭配,构成“没有问题?那就干吧”的句式,下边逐个进行解释。
-
1.要么怎样,要么不怎样
典型的if-else
搭配:
if 条件:
条件为真执行
else:
条件为假执行
-
2.干完了能怎样,干不完就别想怎样
else
可以跟for
和while
循环语句配合使用,但else
语句块只在循环完成后执行,也就是说,如果循环中间使用break
语句跳出循环,那么else
里边的内容就不会被执行了。
def showMaxFactor(num):
count = num // 2
while count > 1:
if num % count == 0:
print('%d最大的约数是%d'%(num, count))
break
count -= 1
else:
print('%d是素数!'% num)
num = int(input('请输入一个数:'))
showMaxFactor(num)
这段代码主要是求用户输入的数的最大约数,如果是素数的话打印这是一个素数。注意要使用地板除(count=num//2
),否则结果会出错。使用暴力的方法一个个尝试(num % count==0
),如果符合条件则打印出最大的约数,并break
,同时不会执行else
语句块的内容了。但如果一直没有遇到合适的条件,则会执行else
语句块内容。
for
语句的用法跟while
一样。
-
3.没有问题?那就干吧
else
语句还能跟异常处理进行搭配,实现跟与循环语句搭配差不多:只要try
语句块里没有出现任何异常,那么就会执行else
语句块里的内容。
try:
int('abc')
except ValueError as reason:
print(出错啦: + str(reason))
else:
print('没有任何异常!')
6. 简洁的with语句
打开文件又要关闭文件,还要关注异常处理会有点麻烦,所以Python提供了一个with
语句,利用这个语句抽象出文件操作中频繁使用的try/except/finally
相关的细节。对文件操作使用with
语句,将大大减少代码量,而且再也不用担心出现文件打开了记关闭的问题了(with
会自动帮我们关闭文件)。
try:
f=open('data.txt', 'w')
for each_line in f:
print(each_line)
except OSError as reason:
print('出错啦:' + str(reason))
finally:
f.close()
使用with
语句,可以改成这样:
try:
with open('data.txt', 'w')as f:
for each_line in f:
print(each_line)
except OSError as reason:
print('出错啦:' + str(reason))
有了with
语句,我们就再也不用担心忘记关闭文件了。