17.异常处理

来源:互联网 发布:linux find 所有目录 编辑:程序博客网 时间:2024/06/05 00:56
----------------常见的Python异常----------------
 
       异常                                                                                 描 述 

   AssertionError                                                             assert语句失败

   AttributeError                                                   试图访问一个对象没有的属性

      IOError                                                     输入输出异常,基本是无法打开文件

    ImportError                                               无法引入模块或者包,基本是路径问题 

  IndentationError                                               语法错误,代码没有正确的对齐 

    IndexError                                                             下标索引超出序列边界

     KeyError                                                          试图访问你字典里不存在的键

  KeyboardInterrupt                                                         ctrl+C被按下

     NameError                                                       尝试访问一个没有申明的变量

    SyntaxError                                                         python代码逻辑语法出错

     TypeError                                                        传入的对象类型与要求不符


  UnboundLocalError        试图访问一个还未设置的全局变量,基本上是由于另有一个同名的全局变量,导致你以为在访问

     ValueError                                               传入一个不被期望的值,即使类型正确


----------------异常的处理----------------

(1)基础

     try/except/else(可选):捕捉由代码中的异常并恢复,匹配except里面的错误,并执行except中定义的代码,后继续执行程序

                                                  (发生异常后,由except捕捉到异常后,不会中断程序,继续执行try语句后面的程序)

                                                   try首行底下的代码块代表此语句的主要动作:试着执行的程序代码。

                                                   except分句定义try代码块内引发的异常处理器,而else分句(如果有)则是提供没有发生异常时候要执行的处理器。


     try/finally:无论异常是否发生,都执行清理行为 (发生异常时程序会中断程序,只不过会执行finally后的代码)

     raise:手动在代码中接触发异常。

     assert:有条件地在程序代码中触发异常。 assert几乎都是用来收集用户定义的约束条件。

     with/as:在Python2.6和后续版本中实现环境管理器。

     注:finally可以和except和else分句出现在相同的try语句内。

             except捕捉到对应的异常才执行。else没有捕捉到异常才执行。


(2)try语句分句形式

     分句形式                                                              说明

      except:                                              捕捉所有(其他)异常类型

     except name:                                          只捕捉特定的异常

  except name,value:             捕捉所有的异常和其额外的数据(或实例)

 except (name1,name2)                           捕捉任何列出的异常

 except (name1,name2),value:     捕捉任何列出的异常,并取得其额外数据

       else:                                               如果没有引发异常,就运行

      finally:                                总是会运行此代码块,无论是否发生异常

        空的except分句会捕捉任何程序执行时所引发的而未被捕捉到的异常。要取得发生的实际异常,可以从内置的sys模块取出sys.exc_info函数的调用结果。

        这会返回一个元组,而元组之前两个元素会自动包含当前异常的名称,以及相关的额外数据(如果有)。

        就基于类的异常而言,这两个元素分别对应的是异常的类以及引发类的实例。

        sys.exc_info结果是获得最近引发的异常更好的方式。如果没有处理器正在处理,就返回包含了三个None值的元组。否则,将会返回(type,value和traceback)

       *type是正在处理的异常的异常类型(一个基于类的异常的类对象)
       *value是异常参数(它的关联值或raise的第二个参数,如果异常类型为类对象,就一定是类实例)
       *traceback是一个traceback对象,代表异常最初发生时所调用的堆栈。

   例:
   try:       main-action:   except Exception1:       hander1   except Exception2:       hander2   ...   else:       else-block   finally:       finally-block

       这语句中main-action代码会先执行。如果该程序代码(main-action)引发异常,那么except代码块都会逐一测试,寻找与抛出的异常相符的语句。

       如果引发异常的是Exception1则会执行hander1代码块,如果引发异常的是Exception2,则会执行hander2代码块。以此类推。

       如果没有引发异常,将会执行else-block代码块。无论前面发生什么,当main-action代码块完成时。finally-block都会执行。


(3)raise语句

     要故意触发异常,可以使用raise语句。

     raise语句组成是:raise关键字,后面跟着要引发的异常名称(选用),以及一个可选的额外的数据项,后可随着异常传递。

     raise <name>
     raise <name>,<data>

(4)assert语句

     assert可以有条件地在程序代码中触发异常,可以认为是有条件的raise。

     注意:assert几乎都是用来收集用户定义的约束条件,而不是捕捉内在的程序设计错误。因为Python会自动收集程序的设计错误,
                通常没有必要写assert去捕捉超出索引值,类型不匹配以及除数为0之类的事。

     assert  <test>,<data>

     例:
     >>> def f(x):     ...     assert x>0,'x must be great zerot'      ...     return x**2

(5)with语句

     标准化的 try-except和try-finally 的用法是保证资源的分配和回收,比如文件(数据、日志、数据库等等)、线程资源、数据库连接等,但它们书写起来却不够优雅。

     with语句的目的在于从流程图中把try、except、 finally关键字和资源分配、释放相关代码统统去掉。

     例:
     >>>with open('/etc/passwd') as f:            for line in f:                print(line)

     注意:with语句仅能工作于支持上下文管理协议(context management protocol)的对象。
               目前支持该协议的对象有:
                                                           file
                                                           decimal.Context
                                                           thread.LockType
                                                           threading.Lock
                                                           threading.RLock
                                                           threading.Condition
                                                           threading.Semaphore

                                                           threading.BoundedSemaphore


原创粉丝点击