zoukankan      html  css  js  c++  java
  • 跟光磊学Python开发-异常机制

    跟光磊学Python开发-异常机制

    异常概述

    异常指的是不正常,也就是程序在执行过程中发生了不可预知的问题,导致程序崩溃。
    Python中常见的异常类如下,它们都直接或者间接继承自位于builtins.py文件中的Exeption类
    Exception

    • NameError
    • TypeError
    • ValueError
    • AttributeError
    • SyntaxError
    • IndexError

    异常处理

    在日常开发中应该尽量避免异常出现,而程序中可能发生异常的情况,可以通过Pyhton提供的异常处理机制来处理异常,从而提高程序的容错性。

    异常处理的语法格式为

    try:
    		可能发生异常的代码
    except Exception:
    		当异常发生时,处理异常的代码

    例如当使用字符串的index(self, sub, start=None, end=None):方法来查找子串时,如果指定的子串找不到会抛出一个ValueError异常
    index方法

    此时可以使用try/except来处理ValueError的异常,如果异常的类型不确定时可以使用Exception替换,例如这里的ValueError可以使用Exception替换,因为异常都直接或者间接继承Exception

    """
    使用try/except基本异常处理
    @author tony 18601767221@163.com
    @version 2021-02-15 15:38:20
    @since python3.9.1
    """
    
    s = "hello"
    
    # 使用try来尝试执行可能发生异常的代码
    try:
        # ValueError: substring not found
        i = s.index("O")
        print(i)
    # 如果发生异常,那么异常信息会被except捕捉到,可以在except后面进行异常处理,如果没有发生异常,程序正常运行,而except就不会执行
    except ValueError:
        print("查找的子串不存在")
    

    程序运行结果
    程序运行结果

    项目运行过程中可能会发生多个异常,此时可以将多个异常包装成一个元祖。需要注意的是同一时刻只能有一个异常发生,因为只要有一个异常发生,程序不会再往下执行,转而执行except的异常处理的代码。

    try:
    		可能发生异常的代码
    except (异常1,异常2....)as e:
    		当异常发生时,处理异常的代码

    其中as e表示给异常起别名

    """
    多异常处理
    @author tony 18601767221@163.com
    @version 2021-02-15 16:09:54
    @since python3.9.1
    """
    
    try:
        number / 0
    except(ZeroDivisionError, NameError) as e:
        print("程序出现了异常", e)
    

    程序运行结果
    程序运行结果

    而异常处理的完整语法格式,其中else和finally都是可选的,而finally通常是操作文件、数据库或者网络时关闭资源使用

    try:
    	可能出现异常的代码
    except Exception as e:
    	异常处理的代码
    else:
    	没有出现异常的代码
    finally:
    	无论是否出现异常,都会执行此语句块

    异常处理之 try/except/else/finally:文件不存在异常

    """
    异常处理之 try/except/else/finally
    @author tony 18601767221@163.com
    @version 2021-02-15 16:16:37
    @since python3.9.1
    """
    try:
        f = None
        f = open("java.txt", "r")
    except Exception as e:
        print("要打开的文件不存在")
        print("异常信息是", e)
    else:
        content = f.read(1024)
        print("文件内容是", end="	")
        print(content)
    finally:
        print("无论程序是否有异常都会执行finally")
        if f != None:
            print("关闭文件资源")
            f.close()
    
    

    程序运行结果
    程序运行结果

    异常处理之 try/except/else/finally:文件存在并关闭文件资源

    """
    异常处理之 try/except/else/finally
    @author tony 18601767221@163.com
    @version 2021-02-15 16:16:37
    @since python3.9.1
    """
    try:
        f = None
        f = open("python.txt", "r")
    except Exception as e:
        print("要打开的文件不存在")
        print("异常信息是", e)
    else:
        content = f.read(1024)
        print("文件内容是", end="	")
        print(content)
    finally:
        print("无论程序是否有异常都会执行finally")
        if f != None:
            print("关闭文件资源")
            f.close()
    
    

    程序运行结果
    程序运行结果

    异常传递

    当代码出现多个层级调用时,其中如果某个环节发生了异常,但是该异常没有处理,默认情况下该异常会向上抛出,如果上层也没有处理,那么会继续再向上层抛出,直到抛到解释器,解释器默认的处理方式就是中断程序,将异常信息打印输出到终端上。

    """
    异常传递
    @author tony 18601767221@163.com
    @version 2021-02-15 15:59:32
    @since python3.9.1
    """
    
    
    def func_a():
        print("execute func_a function")
        func_b()
    
    
    def func_b():
        print("execute func_b function")
        func_c()
    
    
    def func_c():
        print("execute func_c function")
        result = 1 / 0
        print(result)
    
    
    func_a()
    

    程序运行结果
    程序运行结果

    此时推荐在func_c()方法处理该异常

    """
    异常传递
    @author tony 18601767221@163.com
    @version 2021-02-15 15:59:32
    @since python3.9.1
    """
    
    
    def func_a():
        print("execute func_a function")
        func_b()
    
    
    def func_b():
        print("execute func_b function")
        func_c()
    
    
    def func_c():
        print("execute func_c function")
        try:
            result = 1 / 0
            print(result)
        except ZeroDivisionError:
            print("0不能作为被除数")
    
    
    func_a()
    

    程序运行结果
    程序运行结果

    当然由于异常的传递机制,也可以在func_b()方法或者是func_a()方法来处理异常

    """
    异常传递
    @author tony 18601767221@163.com
    @version 2021-02-15 15:59:32
    @since python3.9.1
    """
    
    
    def func_a():
        print("execute func_a function")
        func_b()
    
    
    def func_b():
        print("execute func_b function")
        try:
            func_c()
        except ZeroDivisionError:
            print("0不能作为被除数")
    
    
    def func_c():
        print("execute func_c function")
        result = 1 / 0
        print(result)
    
    
    func_a()
    

    程序运行结果
    程序运行结果

    自定义异常

    在业务开发时需要根据对应的业务场景来自定义相关的业务异常。

    自定义异常的语法格式

    class 异常名Error(Exception):
    	
    	pass
    	

    自定义异常

    """
    定义一个手机号不是纯数字异常
    """
    
    
    class PhoneNumberNotDigitError(Exception):
        pass
    
    
    """
    定义一个手机号长度不合法异常
    """
    
    
    class PhoneNumberLengthError(Exception):
        def __init__(self, msg):
            self.__msg = msg
    
        def __str__(self):
            return self.__msg
    
        pass
    
    
    

    系统异常通常是由系统抛出,而自定义异常通常由开发人员手动抛出,其方式是 raise 异常对象,异常对象可以是类对象,也可以是实例对象

    def get_phone_number():
        """
        从键盘获取用户输入的手机号,判断是否合法
        :return:
        """
        phone_number = input("请输入一个11位数字的手机号:")
        if phone_number.isdigit() == False:
            # 抛出自定义的异常 异常对象是类对象
            raise PhoneNumberNotDigitError
        elif len(phone_number) != 11:
            # 抛出自定义异常,异常对象是实例对象
            raise PhoneNumberLengthError("异常信息:手机号长度必须是11位")
        return phone_number

    通过导入模块调用get_phone_number()函数来处理自定义异常

    """
    处理自定义异常
    @author tony 18601767221@163.com
    @version 2021-02-15 16:49:50
    @since python3.9.1
    """
    from custom_exception import *
    
    # 处理调用get_phone_number()函数时可能发生的异常
    try:
        phone_number = get_phone_number()
    except (PhoneNumberLengthError, PhoneNumberNotDigitError) as e:
        print(e)
    else:
        print("你输入的手机号是", phone_number)
    

    程序运行结果
    程序运行结果
    程序运行结果
    程序运行结果

  • 相关阅读:
    How to change hostname on SLE
    How to install starDIct on suse OS?
    python logging usage
    How to reset password for unknow root
    How to use wget ?
    How to only capute sub-matched character by grep
    How to inspect who is caller of func and who is the class of instance
    How to use groovy script on jenkins
    Vim ide for shell development
    linux高性能服务器编程 (二) --IP协议详解
  • 原文地址:https://www.cnblogs.com/ittimeline/p/14404041.html
Copyright © 2011-2022 走看看