zoukankan      html  css  js  c++  java
  • Python学习9——异常

    Python使用异常对象来表示异常状态,并在遇到错误时引发异常。

    raise语句可以引发异常,将一个类或实例作为参数。

    >>> raise Exception     #引发的是通用异常,没有指出是什么错误
    Traceback (most recent call last):
      File "<pyshell#120>", line 1, in <module>
        raise Exception
    Exception
    >>> 
    >>> raise Exception('hyperdrive overload')   #添加了错误消息yperdrive overload
    Traceback (most recent call last):
      File "<pyshell#125>", line 1, in <module>
        raise Exception('hyperdrive overload')
    Exception: hyperdrive overload

    一些内置的异常类

    类名 描述
    Exception 几乎所有的异常类都是从它派生而来的
    AttributeError 引用属性或给它赋值失败时引发
    OSError 操作系统不能执行指定的任务(如打开文件)时引发,有多个子类
    IndexError 使用序列中不存在的索引时引发,为LookupError的子类
    KeyError 使用映射中不存在的键时引发,为LookupError的子类
    NameError 找不到名称(变量)时引发
    SyntaxError 代码不正确时引发
    TypeError 将内置操作或函数用于类型不正确的对象时引发
    ValueError 将内置操作或函数用于这样的对象时引发:其类型正确但包含的值不合适
    ZeroDivisionError 在除法或求模运算的第二个参数为零时引发

    捕获异常后,如果重新引发它(继续向上传播),可调用raise且不提供任何参数。

    >>> class MuffledCalculator:
        muffled = False     #关闭“抑制”功能,引发异常
        def calc(self,expr):
            try:
                return eval(expr)
            except ZeroDivisionError:
                if self.muffled:
                    print('Division by zero is illegal')
                else:
                    raise
    
                
    >>> calculator = MuffledCalculator()
    >>> calculator.calc('10/2')
    5.0
    >>> calculator.calc('10/0')       #捕获异常ZeroDivisionError后,继续向上传播它
    Traceback (most recent call last):
      File "<pyshell#17>", line 1, in <module>
        calculator.calc('10/0')
      File "<pyshell#14>", line 5, in calc
        return eval(expr)
      File "<string>", line 1, in <module>
    ZeroDivisionError: division by zero      
    >>> calculator.muffled = True   #打开“抑制”功能,打印一条错误信息,不让异常继续传播
    >>> calculator.calc('10/0')
    Division by zero is illegal

    eval函数:将字符串str当成有效的表达式来求值并返回计算结果。

    可使用raise...from...语句来提供自己的异常上下文,也可使用None来禁用上下文。

    >>> try:
        1/0
    except ZeroDivisionError:
        raise ValueError from None
    
    Traceback (most recent call last):
      File "<pyshell#28>", line 4, in <module>
        raise ValueError from None
    ValueError

    一个except子句捕获多种异常,可在一个元组中指定这些异常:

    >>> try:
        x= int(input('enter 1:'))
        y= int(input('enter 2:'))
        print(x/y)
    except(ZeroDivisionError,TypeError,NameError):
        print('.......')
    
        
    enter 1:1
    enter 2:0
    .......

    合理使用else子句:

    >>> while True:
        try:
            x = int(input('enter your first number:'))
            y = int(input('enter your second number:'))
            value = x/y
            print('x / y is ',value)
        except:
            print('Invalid input.Plase try again')
        else:
            break
    
        
    enter your first number:10
    enter your second number:0
    Invalid input.Plase try again
    enter your first number:2
    enter your second number:m
    Invalid input.Plase try again
    enter your first number:5
    enter your second number:'9'
    Invalid input.Plase try again
    enter your first number:10
    enter your second number:2
    x / y is  5.0

    当没有引发异常时,才会跳出循环。如果出现错误,程序会要求用户提供新的输入。

    >>> while True:
        try:
            x = int(input('enter your first name:'))
            y = int(input('enter your second name:'))
            value = x/y
            print('x/y is ',value)
        except Exception as e:
            print('Invalid input:',e)
            print('Plase try agagin')
        else:
            break
    
        
    enter your first name:10
    enter your second name:0
    Invalid input: division by zero
    Plase try agagin
    enter your first name:10
    enter your second name:p
    Invalid input: invalid literal for int() with base 10: 'p'
    Plase try agagin
    enter your first name:'10'
    Invalid input: invalid literal for int() with base 10: "'10'"
    Plase try agagin
    enter your first name:10
    enter your second name:2
    x/y is  5.0

    使用except Exception as e可以在程序中打印更有用的错误消息。

     

    finally子句,可用于在发生异常时执行清理工作。与try子句配套使用.

    >>> try:
        1/0
    except NameError:
        print('Unknown variable')
    else:
        print('That went well!')
    finally:
        print('Cleaning up.')
    
        
    Cleaning up.
    Traceback (most recent call last):
      File "<pyshell#89>", line 2, in <module>
        1/0
    ZeroDivisionError: division by zero

     

    栗子:假设有一个字典,你要在指定的键存在时打印与之相关联的值,否则什么都不做。

    >>> def describe_person(person):
        print('Description of',person['name'])
        print('age:',person['age'])
        if 'occupation' in person:
            print('Occupation:',person['occupation'])
    
            
    >>> p = dict(name='Throatwobbler Mangrove',age=25)
    >>> describe_person(p)
    Description of Throatwobbler Mangrove
    age: 25

    这段代码很直观,但它必须两次查找'occupation'键:1次检查这个键是否存在(条件中),另一次获取这个键的值,打印。

    优化一下:

    >>> def describe_person(person):
        print('Description of',person['name'])
        print('age:',person['age'])
        try:
            print('Occupation:',person['occupation'])   #函数直接假设存在'occupation',如果假设成立,直接获取并打印值,不用检查键是否存在。
        except KeyError:pass
    
        
    >>> p = dict(name='Throatwobbler Mangrove',age=25)
    >>> describe_person(p)
    Description of Throatwobbler Mangrove
    age: 25

    >>> while True:

             try:

                       x = int(input('enter your first name:'))

                       y = int(input('enter your second name:'))

                       value = x/y

                       print('x/y is ',value)

             except Exception as e:

                       print('Invalid input:',e)

                       print('Plase try agagin')

             else:

                       break

     

            

    enter your first name:10

    enter your second name:0

    Invalid input: division by zero

    Plase try agagin

    enter your first name:10

    enter your second name:p

    Invalid input: invalid literal for int() with base 10: 'p'

    Plase try agagin

    enter your first name:'10'

    Invalid input: invalid literal for int() with base 10: "'10'"

    Plase try agagin

    enter your first name:10

    enter your second name:2

    x/y is  5.0

  • 相关阅读:
    Java 基础:继承中的执行顺序
    Java 基础:抽象类与接口
    ElasticSearch : 基础简介
    Java GUI : 实现排序算法的动态演示
    Java GUI:将JPanel添加进JScrollPane
    菜鸟的算法入门:java的链表操作
    Docker与Tomcat:去掉项目名称进行访问
    vue输入框的搜索返回信息高亮显示
    position: static 和 position: unset
    vue css /deep/ 用法
  • 原文地址:https://www.cnblogs.com/suancaipaofan/p/11111765.html
Copyright © 2011-2022 走看看