Python提供了两个非常重要的功能来处理Python程序中的任何意外错误,并在其中添加调试功能 -

  • 异常处理 (Exception Handling) - 这将在本教程中介绍。 以下是Python中可用的标准异常列表 - 标准异常。

  • 断言 (Assertions) - 这将在本章中介绍。

Python中有Exception, StopIteration, SystemExit, StandardError, ArithmeticError, OverflowError,FloatingPointError,ZeroDivisonError,AssertionError, AttributeError等标准异常

Python中的断言(Assertions)

断言是一种健全性检查,您可以在完成程序测试后打开或关闭该功能。

  • 想想一个断言的最简单方法是将它比作一个raise-if语句(或者更准确的说,是一个if-not-statement语句)。 测试表达式,如果结果为false,则会引发异常。

  • 断言由assert语句执行,这是1.5版本中引入的最新的Python关键字。

  • 程序员经常在函数的开始处放置断言来检查有效输入,并在函数调用后检查有效输出。

assert声明

当它遇到一个assert语句时,Python会对伴随的表达式进行评估,这有希望是正确的。 如果表达式为false,则Python会引发AssertionError异常。

assert的语法是 -

  • 01
assert Expression[, Arguments]

如果断言失败,Python将使用ArgumentExpression作为AssertionError的参数。 AssertionError异常可以像使用try-except语句一样被其他异常捕获和处理。 如果他们没有处理,他们将终止程序并产生追溯。

这是一个将给定温度从开氏度转换成华氏度的函数。 由于0°K与其温度一样冷,因此,如果它看到负温度,功能就会消失 -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
#!/usr/bin/python3 def KelvinToFahrenheit(Temperature): assert (Temperature >= 0),"Colder than absolute zero!" return ((Temperature-273)*1.8)+32 print (KelvinToFahrenheit(273)) print (int(KelvinToFahrenheit(505.78))) print (KelvinToFahrenheit(-5))

当上面的代码被执行时,它会产生以下结果 -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
32.0 451 Traceback (most recent call last): File "test.py", line 9, in print KelvinToFahrenheit(-5) File "test.py", line 4, in KelvinToFahrenheit assert (Temperature >= 0),"Colder than absolute zero!" AssertionError: Colder than absolute zero!

什么是异常(Exception)?

异常是一个事件,在执行程序期间发生,这会中断程序指令的正常流程。 通常,当Python脚本遇到无法应付的情况时,会引发异常。 一个异常是表示错误的Python对象。

当Python脚本引发异常时,它必须立即处理异常,否则它会终止并退出。

处理异常

如果您有一些可能引发异常的可疑代码,您可以通过将可疑代码放在try:区块中来捍卫您的程序。 在try:块之后,包含一个except:语句,接着是一段代码,它尽可能优雅地处理问题。

这里是try ...的简单语法.... except ... else blocks -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
  • 09
  • 10
try: You do your operations here ...................... except ExceptionI: If there is ExceptionI, then execute this block. except ExceptionII: If there is ExceptionII, then execute this block. ...................... else: If there is no exception then execute this block.

这里有几点关于上述语法的重要观点 -

  • 一个try语句可以有多个except语句。 当try块包含可能引发不同类型异常的语句时,这很有用。

  • 您也可以提供一个通用的except子句,它处理任何异常。

  • 在except子句之后,可以包含一个else子句。 如果try:块中的代码不引发异常,则else-block中的代码将执行。

  • else-block是不需要try:block保护的代码的好地方。

这个例子打开一个文件,在文件中写入内容,并优雅地出现,因为根本没有问题 -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
  • 09
  • 10
#!/usr/bin/python3 try: fh = open("testfile", "w") fh.write("This is my test file for exception handling!!") except IOError: print ("Error: can\'t find file or read data") else: print ("Written content in the file successfully") fh.close()

这产生了以下结果 -

  • 01
Written content in the file successfully

这个例子试图打开一个你没有写权限的文件,所以会引发一个异常 -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
  • 09
#!/usr/bin/python3 try: fh = open("testfile", "r") fh.write("This is my test file for exception handling!!") except IOError: print ("Error: can\'t find file or read data") else: print ("Written content in the file successfully")

这产生了以下结果 -

  • 01
Error: can't find file or read data

您也可以使用except语句,没有exceptions的定义如下

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
try: You do your operations here ...................... except: If there is any exception, then execute this block. ...................... else: If there is no exception then execute this block.

这种try-except语句捕获所有发生的异常。 虽然使用这种try-except语句并不被认为是一种很好的编程习惯,因为它捕获所有的异常,但不会让程序员确定可能发生的问题的根本原因。

您也可以使用相同的except语句来处理多个异常,如下所示 -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
  • 09
try: You do your operations here ...................... except(Exception1[, Exception2[,...ExceptionN]]]): If there is any exception from the given exception list, then execute this block. ...................... else: If there is no exception then execute this block.

try-finally语句

你可以使用finally:块和try:块。 finally:块是放置任何必须执行的代码的地方,无论try-block是否引发异常。 try-finally语句的语法是这样的 -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
try: You do your operations here; ...................... Due to any exception, this may be skipped. finally: This would always be executed. ......................

- 您可以提供except子句或finally子句,但不能同时提供。 您不能使用else子句以及finally子句。

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
#!/usr/bin/python3 try: fh = open("testfile", "w") fh.write("This is my test file for exception handling!!") finally: print ("Error: can\'t find file or read data") fh.close()

如果您无权以书面模式打开文件,则会产生以下结果 -

  • 01
Error: can't find file or read data

同样的例子可以写得更干净如下 -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
  • 09
  • 10
  • 11
#!/usr/bin/python3 try: fh = open("testfile", "w") try: fh.write("This is my test file for exception handling!!") finally: print ("Going to close the file") fh.close() except IOError: print ("Error: can\'t find file or read data")

当try块中抛出异常时,执行立即传递给finally块。 在finally块中的所有语句都执行完后,异常再次引发,并在except语句中处理,如果出现在try-except语句的下一个更高层中。

异常的参数

一个异常可以有一个参数,它是一个提供有关该问题的附加信息的值。 参数的内容因例外而异。 通过在except子句中提供一个变量来捕获异常的参数,如下所示 -

  • 01
  • 02
  • 03
  • 04
  • 05
try: You do your operations here ...................... except ExceptionType as Argument: You can print value of Argument here...

如果您编写处理单个异常的代码,则可以在except语句中使用一个变量来跟随异常的名称。 如果你正在捕获多个异常,你可以在异常的元组后面有一个变量。

该变量接收大多包含异常原因的异常值。 变量可以以元组的形式接收单个值或多个值。 该元组通常包含错误字符串,错误编号和错误位置。

以下是一个例外 -

#!/usr/bin/python3 # Define a function here. def temp_convert(var): try: return int(var) except ValueError as Argument: print ("The argument does not contain numbers\n", Argument) # Call above function here. temp_convert("xyz")

这产生了以下结果 -

  • 01
  • 02
The argument does not contain numbers invalid literal for int() with base 10: 'xyz'

引发异常

您可以通过使用raise语句以几种方式引发异常。 raise语句的一般语法如下 -

  • 01
raise [Exception [, args [, traceback]]]

这里,Exception是异常的类型(例如NameError),argument是异常参数的值。 该论点是可选的; 如果未提供,则异常参数为None。

最后一个参数traceback也是可选的(在实际中很少使用),如果存在,则是用于该异常的追踪对象。

异常可以是字符串,类或对象。 Python核心提出的大多数例外都是类,其中一个参数是该类的一个实例。 定义新的例外非常简单,可以按如下方式完成 -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
def functionName( level ): if level <1: raise Exception(level) # The code below to this would not be executed # if we raise the exception return level

- 为了捕获异常,“except”子句必须引用作为类对象或简单字符串引发的相同异常。 例如,要捕获上述异常,我们必须按如下方式编写except子句:

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
try: Business Logic here... except Exception as e: Exception handling here using e.args... else: Rest of the code here...

以下示例说明了引发异常的用法 -

  • 01
  • 02
  • 03
  • 04
  • 05
  • 06
  • 07
  • 08
  • 09
  • 10
  • 11
  • 12
  • 13
#!/usr/bin/python3 def functionName( level ): if level <1: raise Exception(level) # The code below to this would not be executed # if we raise the exception return level try: l = functionName(-10) print ("level = ",l) except Exception as e: print ("error in level argument",e.args[0])

这将产生以下结果

  • 01
error in level argument -10

用户自定义异常

Python还允许您通过从标准内置异常中派生类来创建自己的异常。

这里是一个与RuntimeError相关的例子。 在这里,创建一个从RuntimeError子类化的类。 当发现异常时需要显示更具体的信息时,这非常有用。

在try块中,用户定义的异常被引发并捕获到except块中。 变量e用于创建类Networkerror的实例。

  • 01
  • 02
  • 03
class Networkerror(RuntimeError): def __init__(self, arg): self.args = arg

所以一旦你定义了上面的类,你可以举例如下 -

  • 01
  • 02
  • 03
try: raise Networkerror("Bad hostname") except Networkerror,e: print e.args