关于python的异常处理(python之错误与异常)
错误 通常是指程序中的 语法错误 或 逻辑错误,来通过两个 Python 例子看一下:
语法错误示例
# print前面少了 :
if True
print("hello python")
我们编写程序通常使用开发工具编写,比如:我使用 Pycharm 工具编写 Python 程序,像这种语法错误,在编写程序时,编译器就会检测出来并提示我们,因此,我们编写好的程序几乎不会出现这种问题。
逻辑错误示例
# 0 是不能作为被除数的
a = 5
b = 0
print(a/b)
#执行结果:
zeroDivisionError: division by zero
逻辑错误编译器是不会提示我们的,因此,我们编写程序时,对一些基本常识要有一定了解,从而,避免出现逻辑错误。
2 异常即便 Python 程序的语法是正确的,在运行它的时候,也有可能发生错误,运行期检测到的错误被称为异常;大多数的异常都不会被程序处理,都以错误信息的形式展现。
2.1 内置异常
我们先来看一下异常层次结构:
BaseException
-- SystemExit
-- KeyboardInterrupt
-- GeneratorExit
-- Exception
-- StopIteration
-- StopAsyncIteration
-- ArithmeticError
| -- FloatingPointError
| -- OverflowError
| -- ZeroDivisionError
-- AssertionError
-- AttributeError
-- BufferError
-- EOFError
-- ImportError
| -- ModuleNotFoundError
-- LookupError
| -- IndexError
| -- KeyError
-- MemoryError
-- NameError
| -- UnboundLocalError
-- OSError
| -- BlockingIOError
| -- ChildProcessError
| -- ConnectionError
| | -- BrokenPipeError
| | -- ConnectionAbortedError
| | -- ConnectionRefusedError
| | -- ConnectionResetError
| -- FileExistsError
| -- FileNotFoundError
| -- InterruptedError
| -- IsADirectoryError
| -- NotADirectoryError
| -- PermissionError
| -- ProcessLookupError
| -- TimeoutError
-- ReferenceError
-- RuntimeError
| -- NotImplementedError
| -- RecursionError
-- SyntaxError
| -- IndentationError
| -- TabError
-- SystemError
-- TypeError
-- ValueError
| -- UnicodeError
| -- UnicodeDecodeError
| -- UnicodeEncodeError
| -- UnicodeTranslateError
-- Warning
-- DeprecationWarning
-- PendingDeprecationWarning
-- RuntimeWarning
-- SyntaxWarning
-- UserWarning
-- FutureWarning
-- ImportWarning
-- UnicodeWarning
-- BytesWarning
-- ResourceWarning
通过上面的异常层次结构,我们可以清晰的看出,BaseException为所有异常的基类,其下面分为:SystemExit、KeyboardInterrupt、GeneratorExit、Exception 四类异常,Exception 为所有非系统退出类异常的基类,Python 提倡继承 Exception 或其子类派生新的异常;Exception 下包含我们常见的多种异常如:MemoryError(内存溢出)、BlockingIOError(IO异常)、SyntaxError(语法错误异常)…
详细说明可以查看下面列表:
2.2 异常处理
Python 程序捕捉异常使用 try/except 语句,先看个例子:
# 1.被除数为 0,未捕获异常 def getNum(n): return 10 / n print(getNum(0)) #输出结果: ZeroDivisionError: division by zero # 2.捕获异常 def getNum(n): try: return 10 / n except IOError: print('Error: IOError argument.') except ZeroDivisionError: print('Error: ZeroDivisionError argument.') print(getNum(0)) ''' 输出结果: Error: ZeroDivisionError argument. None '''
try 语句的工作方式为:
首先,执行 try 子句 (在 try 和 except 关键字之间的部分);如果没有异常发生, except 子句 在 try 语句执行完毕后就被忽略了;如果在 try 子句执行过程中发生了异常,那么该子句其余的部分就会被忽略;如果异常匹配于 except 关键字后面指定的异常类型,就执行对应的except子句,然后继续执行 try 语句之后的代码;如果发生了一个异常,在 except 子句中没有与之匹配的分支,它就会传递到上一级 try 语句中;如果最终仍找不到对应的处理语句,它就成为一个 未处理异常,终止程序运行,显示提示信息。
try/except 语句还可以带有一个 else、finally子句,示例如下:
def getNum(n): try: print('try --> ',10 / n) except ZeroDivisionError: print('except --> Error: ZeroDivisionError argument.') else: print('else -->') finally: print('finally -->') ''' 1.调用:getNum(0) 输出结果: except --> Error: ZeroDivisionError argument. finally --> 2.调用:getNum(1) 输出结果: try --> 10.0 else --> finally --> '''
其中,else 子句只能出现在所有 except 子句之后,只有在没有出现异常时执行;finally 子句放在最后,无论是否出现异常都会执行。
2.3 抛出异常
使用 raise 语句允许强制抛出一个指定的异常,要抛出的异常由 raise 的唯一参数标识,它必需是一个异常实例或异常类(继承自 Exception 的类),如:
raise NameError('HiThere')
2.4 自定义异常
正常来说,Python 提供的异常类型已经满足我们的使用了,但是有时候我们有定制性的需求,我们可以自定义异常类,继承自 Error 或 Exception 类就可以了,看个例子:
# 自定义异常类 MyExc class MyExc(Exception): #继承Exception类 def __init__(self, value): self.value = value def __str__(self): if self.value == 0: return '被除数不能为0' # 自定义方法 def getNum(n): try: if n == 0: exc = MyExc(n) print(exc) else: print(10 / n) except: pass ''' 1.调用 getNum(1),输出结果为: 10.0 2.调用 getNum(0),输出结果为: 被除数不能为0 '''
在这个自定义的异常例子中,当参数 n 不为 0 时,则正常,当 n 等于 0,则抛出异常,自定义异常在实际应用中很少用到。
,
免责声明:本文仅代表文章作者的个人观点,与本站无关。其原创性、真实性以及文中陈述文字和内容未经本站证实,对本文以及其中全部或者部分内容文字的真实性、完整性和原创性本站不作任何保证或承诺,请读者仅作参考,并自行核实相关内容。文章投诉邮箱:anhduc.ph@yahoo.com