Python错误和异常的使用详解

>>> for i in range(10)
 File "<stdin>", line 1
   for i in range(10)
                    ^
SyntaxError: invalid syntax
上面那句话因为缺少冒号 : ,导致解释器无法解释,于是报错。这个报错行为是由Python的语法分析器完成的,并且检测到了错误所在文件和行号( File "<stdin>", line 1 ),还以向上箭头 ^ 标识错误位置(后面缺少 : ),最后显示错误类型。

另一种常见错误是逻辑错误。逻辑错误可能是由于不完整或者不合法的输入导致,也可能是无法生成、计算等,或者是其它逻辑问题。

当Python检测到一个错误时,解释器就无法继续执行下去,于是抛出提示信息,即为异常。

异常

下表中列出常见的异常

异常 描述
NameError 尝试访问一个没有申明的变量
ZeroDivisionError 除数为0
SyntaxError 语法错误
IndexError 索引超出序列范围
KeyError 请求一个不存在的字典关键字
IOError 输入输出错误(比如你要读的文件不存在)
AttributeError 尝试访问未知的对象属性
NameError

>>> bar
Traceback (most recent call last):
 File "<stdin>", line 1, in <module>
NameError: name 'bar' is not defined
Python中变量虽然不需在使用变量之前先声明类型,但也需要对变量进行赋值,然后才能使用。不被赋值的变量,不能再Python中存在,因为变量相当于一个标签,要把它贴到对象上才有意义。

ZeroDivisionError

>>> 1/0
Traceback (most recent call last):
 File "<stdin>", line 1, in <module>
ZeroDivisionError: integer division or modulo by zero
SyntaxError

>>> for i in range(10)
  File "<stdin>", line 1
    for i in range(10)
                     ^
SyntaxError: invalid syntax
这种错误发生在Python代码编译的时候,当编译到这一句时,解释器不能讲代码转化为Python字节码,就报错。

IndexError和KeyError

>>> a = [1,2,3]
>>> a[4]
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
IndexError: list index out of range

>>> d = {"python":"itdiffer.com"}
>>> d["java"]
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
KeyError: 'java'
IOError

>>> f = open("foo")
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
IOError: [Errno 2] No such file or directory: 'foo'
AttributeError

>>> class A(object): pass        #Python 3: class A: pass
...
>>> a = A()
>>> a.foo
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'A' object has no attribute 'foo'
处理异常

#!/usr/bin/env python
# coding=utf-8

while 1:
   print "this is a division program."
   c = raw_input("input 'c' continue, otherwise logout:")
   if c == 'c':
       a = raw_input("first number:")
       b = raw_input("second number:")
       try:
           print float(a)/float(b)
           print "*************************"
       except ZeroDivisionError:
           print "The second number can't be zero!"
           print "*************************"
   else:
       break
try…except

对于上述程序,只看 try 和 except 部分,如果没有异常发生, except 子句在 try 语句执行之后被忽略;如果 try 子句中有异常可,该部分的其它语句被忽略,直接跳到 except 部分,执行其后面指定的异常类型及其子句。

except 后面也可以没有任何异常类型,即无异常参数。如果这样,不论 try 部分发生什么异常,都会执行 except 。

在 except 子句中,可以根据异常或者别的需要,进行更多的操作。比如:

#!/usr/bin/env python
# coding=utf-8

class Calculator(object):
   is_raise = True
   def calc(self, express):
       try:
           return eval(express) #运行表达式
       except ZeroDivisionError:
           if self.is_raise:
               print "zero can not be division."        #Python 3:  "zero can not be division."
           else:
               raise #抛出异常信息
处理多个异常

Python 2:

    #!/usr/bin/env python
    # coding=utf-8

    while 1:
        print "this is a division program."
        c = raw_input("input 'c' continue, otherwise logout:")
        if c == 'c':
            a = raw_input("first number:")
            b = raw_input("second number:")
            try:
                print float(a)/float(b)
                print "*************************"
            except ZeroDivisionError:
                print "The second number can't be zero!"
                print "*************************"
            except ValueError:
                print "please input number."
                print "************************"
        else:
            break
           
 or
 
except (ZeroDivisionError, ValueError): #括号内也可以包含多个异常
   print "please input rightly."
   print "********************"
打印异常,但程序不中断

    while 1:
        print "this is a division program."
        c = raw_input("input 'c' continue, otherwise logout:")
        if c == 'c':
            a = raw_input("first number:")
            b = raw_input("second number:")
            try:
                print float(a)/float(b)
                print "*************************"
            except (ZeroDivisionError, ValueError), e: #类似java
                print e
                print "********************"
        else:
            break

Python 3:

    while 1:
        print("this is a division program.")
        c = input("input 'c' continue, otherwise logout:")
        if c == 'c':
            a = input("first number:")
            b = input("second number:")
            try:
                print(float(a)/float(b))
                print("*************************")
            except (ZeroDivisionError, ValueError) as e:
                print(e)
                print("********************")
        else:
            break
else语句

>>> try:
...     print "I am try"        #Python 3: print("I am try"),
... except:               
...     print "I am except"
... else:                     #处理except就不会运行else
...     print "I am else"
...
I am try
I am else
else语句应用,只有输入正确的内容,循环才会终止

#!/usr/bin/env python
# coding=utf-8
while 1:
    try:
        x = raw_input("the first number:")
        y = raw_input("the second number:")

        r = float(x)/float(y)
        print r
    except Exception, e:  #python3为 Exception as e:
        print e
        print "try again."
    else:
        break
finally语句

如果有了 finally ,不管前面执行的是 try ,还是 except ,最终都要执行它。类似java

>>> x = 10

>>> try:
...     x = 1/0
... except Exception, e:        #Python 3:  except Exception as e:
...     print e        #Python 3: print(e)
... finally:
...     print "del x"        #Python 3:  print(e)
...     del x
...
integer division or modulo by zero
del x
assert

assert 是一句等价于布尔真的判定,发生异常就意味着表达式为假。当程序运行到某个节点的时候,就断定某个变量的值必然是什么,或者对象必然拥有某个属性等,简单说就是断定什么东西必然是什么,如果不是,就抛出异常。

#!/usr/bin/env python
# coding=utf-8
           
if __name__ == "__main__":
    a = 8
    assert a < 0
    print a
   
Traceback (most recent call last):
  File "/Users/liuguoquan/Documents/workspace/PythonDemo/main.py", line 6, in <module>
    assert a < 0
AssertionError
这就是断言assert的引用。什么是使用断言的最佳时机?有文章做了总结:

如果没有特别的目的,断言应该用于如下情况:

防御性的编程
运行时对程序逻辑的检测
合约性检查(比如前置条件,后置条件)
程序中的常量
检查文档

时间: 2024-10-06 00:41:29

Python错误和异常的使用详解的相关文章

Python selenium 三种等待方式详解(必会)_python

很多人在群里问,这个下拉框定位不到.那个弹出框定位不到-各种定位不到,其实大多数情况下就是两种问题:1 有frame,2 没有加等待.殊不知,你的代码运行速度是什么量级的,而浏览器加载渲染速度又是什么量级的,就好比闪电侠和凹凸曼约好去打怪兽,然后闪电侠打完回来之后问凹凸曼你为啥还在穿鞋没出门?凹凸曼分分中内心一万只羊驼飞过,欺负哥速度慢,哥不跟你玩了,抛个异常撂挑子了. 那么怎么才能照顾到凹凸曼缓慢的加载速度呢?只有一个办法,那就是等喽.说到等,又有三种等法,且听博主一一道来: 1. 强制等待

Python中的深拷贝和浅拷贝详解

  这篇文章主要介绍了Python中的深拷贝和浅拷贝详解,本文讲解了变量-对象-引用.可变对象-不可变对象.拷贝等内容,需要的朋友可以参考下 要说清楚Python中的深浅拷贝,需要搞清楚下面一系列概念: 变量-引用-对象(可变对象,不可变对象)-切片-拷贝(浅拷贝,深拷贝) [变量-对象-引用] 在Python中一切都是对象,比如说:3, 3.14, 'Hello', [1,2,3,4],{'a':1}...... 甚至连type其本身都是对象,type对象 Python中变量与C/C++/Ja

Python中的推导式使用详解

  这篇文章主要介绍了Python中的推导式使用详解,本文分别讲解了列表推导式.字典推导式.集合推导式使用实例,需要的朋友可以参考下 推导式是Python中很强大的.很受欢迎的特性,具有语言简洁,速度快等优点.推导式包括: 1.列表推导式 2.字典推导式 3.集合推导式 嵌套列表推导式 NOTE: 字典和集合推导是最近才加入到Python的(Python 2.7 和Python 3.1以上版). 下面简要介绍下: [列表推导式] 列表推导能非常简洁的构造一个新列表:只用一条简洁的表达式即可对得到

Python中的zipfile模块使用详解

  这篇文章主要介绍了Python中的zipfile模块使用详解,zipfile模块是用来操作zip文件,需要的朋友可以参考下 zip文件格式是通用的文档压缩标准,在ziplib模块中,使用ZipFile类来操作zip文件,下面具体介绍一下: class zipfile.ZipFile(file[, mode[, compression[, allowZip64]]]) 创建一个ZipFile对象,表示一个zip文件.参数file表示文件的路径或类文件对象(file-like object);参

Python中tell()方法的使用详解

  这篇文章主要介绍了Python中tell()方法的使用详解,是Python入门学习中的基础知识,需要的朋友可以参考下 tell()方法返回的文件内的文件读/写指针的当前位置. 语法 以下是tell()方法的语法: ? 1 fileObject.tell() 参数 NA 返回值 此方法返回该文件中读出的文件/写指针的当前位置. 例子 下面的例子显示了tell()方法的使用. ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 #

Python中的rfind()方法使用详解

  这篇文章主要介绍了Python中的rfind()方法使用详解,是Python入门中的基础知识,需要的朋友可以参考下 rfind()方法返回所在子str 被找到的最后一个索引,或者-1,如果没有这样的索引不存在,可选择限制搜索字符串string[beg:end]. 语法 以下是rfind()方法的语法: ? 1 str.rfind(str, beg=0 end=len(string)) 参数 str -- 此选项指定要搜索的字符串 beg -- 这是开始索引,默认情况下为 0 end -- 这

Python中的rjust()方法使用详解

  这篇文章主要介绍了Python中的rjust()方法使用详解,是Python学习入门中的基础知识,需要的朋友可以参考下 rjust()该方法返回字符串合理字符串的右边的长度宽度.填充是通过使用指定的fillchar(默认为空格).如果宽度小于len(s)返回原始字符串. 语法 以下是rjust()方法的语法: ? 1 str.rjust(width[, fillchar]) 参数 width -- 这是字符串填充后总共的长度. fillchar -- 这是填充字符,默认为空格. 返回值 此方

Python中的choice()方法使用详解

 这篇文章主要介绍了Python中的choice()方法使用详解,是Python入门中的基础知识,需要的朋友可以参考下     choice()方法从一个列表,元组或字符串返回一个随机项. 语法 以下是choice()方法的语法: ? 1 choice( seq ) 注意:此函数是无法直接访问的,所以我们需要导入random模块,然后我们需要使用random对象来调用这个函数. 参数 seq -- 这可能是一个列表,元组或字符串... 返回值 该方法返回一个随机项. 例子 下面的例子显示了cho

Python类定义和类继承详解

  这篇文章主要介绍了Python类定义和类继承详解,本文讲解了类的私有属性.类的方法.私有的类方法.类的专有方法.类的定义.类的单继承.类的多继承等内容,需要的朋友可以参考下 一.类定义: ? 1 2 class <类名>: <语句> 类实例化后,可以使用其属性,实际上,创建一个类之后,可以通过类名访问其属性 如果直接使用类名修改其属性,那么将直接影响到已经实例化的对象 类的私有属性: __private_attrs 两个下划线开头,声明该属性为私有,不能在类地外部被使用或直接访