文章目录

参考文档:内置异常 — Python 3.13.8 文档

1. Python内置异常概述

在Python中,所有异常均继承自BaseException类,是处理程序运行时错误的核心机制。合理理解和使用内置异常,能帮助开发者精准捕获错误、定位问题,并编写更健壮的代码。本章将系统梳理Python内置异常的分类、用法及核心特性。

1.1 异常的基本规则

  • 继承关系:所有内置异常的根类是BaseException,用户自定义异常推荐继承自Exception(而非BaseException,避免捕获系统级异常如SystemExit)。
  • 异常捕获except子句会捕获目标异常及其所有子类(例如except Exception会捕获ValueErrorTypeError等,但不会捕获BaseException的直接子类如KeyboardInterrupt)。
  • 关联值:多数异常有“关联值”(如错误信息字符串),通过异常实例的args属性可访问(例如except ValueError as e: print(e.args))。
  • 版本差异:部分异常是后续版本新增的(如ModuleNotFoundError在3.6+、ExceptionGroup在Python 3.11+),使用时需注意兼容性。

1.2 异常上下文(__context____cause____suppress_context__

当异常嵌套引发时(如except块中再引发新异常),Python通过三个属性记录上下文关系,帮助调试时追溯完整错误链:

  • __context__隐式上下文,自动记录“被处理过的前一个异常”(无需显式声明)。
  • __cause__显式原因,通过raise new_exc from original_exc声明,表明新异常是由原异常直接导致的。
  • __suppress_context__:布尔值,显式声明from时自动设为True,表示屏蔽__context__的隐式展示。
# 1. 隐式上下文(__context__)
try:
    # 第一步:触发KeyError
    d = {"a": 1}
    print(d["b"])
except KeyError as e1:
    # 第二步:在except中触发AttributeError,无显式from
    obj = type("Empty", (), {})()  # 空对象
    print(obj.no_such_attr)  # 触发AttributeError

# 运行结果中,AttributeError的回溯会显示“During handling of the above exception, another exception occurred”
# 即通过__context__关联了KeyError


# 2. 显式原因(__cause__)
try:
    # 第一步:触发ZeroDivisionError
    1 / 0
except ZeroDivisionError as e1:
    # 第二步:显式声明新异常的原因
    raise ValueError("计算失败,因分母为零") from e1

# 运行结果中,ValueError的回溯会显示“The above exception was the direct cause of the following exception”
# 即通过__cause__关联了ZeroDivisionError,且__suppress_context__=True

1.3 异常的常用方法

1.3.1 add_note(note)(Python 3.11+)

为异常添加注释,注释会在回溯信息中显示,帮助补充错误上下文(如“请检查配置文件路径”)。

1.3.2 with_traceback(tb)

为异常绑定新的回溯对象(traceback),常用于异常转换时保留原始错误栈(如将自定义异常转换为标准异常)。

import sys
import traceback

def func():
    # 触发基础异常
    raise ValueError("原始错误:参数无效")

try:
    func()
except ValueError as e:
    # 1. 添加注释
    e.add_note("补充说明:参数需为正整数")
    e.add_note("建议检查调用func()时的传入值")
    
    # 2. 获取原始回溯,转换为新异常并绑定回溯
    tb = traceback.format_exc()  # 获取回溯信息
    new_exc = RuntimeError("函数执行失败")
    new_exc = new_exc.with_traceback(sys.exc_info()[2])  # 绑定原始回溯
    
    raise new_exc  # 引发新异常

# 运行结果中,RuntimeError的回溯会包含:
# - 原始ValueError的错误栈(通过with_traceback绑定)
# - 两个补充注释(通过add_note添加)

2. 异常基类

基类主要用于派生其他异常,自身很少直接引发,核心作用是“分类异常”,便于批量捕获(如except ArithmeticError捕获所有算术类错误)。

2.1 BaseException:所有异常的根类

  • 作用:Python中所有异常的顶层父类,包含系统级异常(如SystemExitKeyboardInterrupt)和应用级异常(Exception的子类)。
  • 注意不建议用户自定义异常直接继承BaseException,否则可能捕获到系统级异常(如sys.exit()触发的SystemExit),导致程序无法正常退出。
  • 核心属性/方法
    • args:异常的关联值元组(如ValueError("a", "b").args == ("a", "b"))。
    • __traceback__:异常的回溯对象。
    • add_note(note)with_traceback(tb)(见1.3节)。
# SystemExit继承自BaseException,except Exception无法捕获
try:
    import sys
    sys.exit(1)  # 触发SystemExit
except Exception as e:
    print("捕获到Exception:", e)  # 不会执行
except BaseException as e:
    print(f"捕获到BaseException: {type(e).__name__}")  # 执行,输出“捕获到BaseException: SystemExit”

2.2 Exception:应用级异常的基类

  • 作用:所有“非系统级异常”的父类(如ValueErrorTypeError),是用户自定义异常的推荐基类
  • 特点except Exception可捕获绝大多数应用逻辑错误,但不会捕获BaseException的直接子类(如KeyboardInterruptSystemExit),避免干扰系统级操作。
# 自定义异常:继承自Exception
class ConfigError(Exception):
    """配置文件相关错误的基类"""
    pass

class ConfigNotFoundError(ConfigError):
    """配置文件不存在的错误"""
    def __init__(self, path):
        self.path = path
        super().__init__(f"配置文件不存在:{path}")

# 使用自定义异常
try:
    config_path = "config.ini"
    with open(config_path, "r") as f:
        pass
except FileNotFoundError:
    raise ConfigNotFoundError(config_path) from None  # 屏蔽原异常的上下文

# 捕获自定义异常
try:
    raise ConfigNotFoundError("config.ini")
except ConfigError as e:
    print(f"配置错误:{e}")  # 输出“配置错误:配置文件不存在:config.ini”

2.3 其他核心基类

基类 作用 子类示例
ArithmeticError 算术运算相关错误的基类 ZeroDivisionErrorOverflowError
LookupError 序列/映射查找错误的基类(如索引、键不存在) IndexErrorKeyError
OSError 系统调用相关错误的基类(如文件操作、网络连接) FileNotFoundErrorPermissionError
Warning 警告类别的基类(非错误,仅提示潜在风险) DeprecationWarningFutureWarning
# 批量捕获算术类错误(ArithmeticError的子类)
try:
    result1 = 1 / 0  # ZeroDivisionError
    # result2 = 2 ** 1000000  # 极端情况下触发OverflowError(整数一般不会,浮点数可能)
except ArithmeticError as e:
    print(f"算术错误:{type(e).__name__}: {e}")  # 输出“算术错误:ZeroDivisionError: division by zero”


# 批量捕获查找类错误(LookupError的子类)
data = [1, 2, 3]
d = {"a": 1}
try:
    # print(data[10])  # IndexError
    print(d["b"])  # KeyError
except LookupError as e:
    print(f"查找错误:{type(e).__name__}: {e}")  # 输出“查找错误:KeyError: 'b'”

3. 常用具体异常

具体异常是程序运行中最常触发的异常,需掌握其触发场景和捕获方式。

3.1 断言与属性相关异常

3.1.1 AssertionError

  • 触发场景assert语句的条件为False时触发(用于调试阶段验证假设,如“参数必须为正”)。
  • 注意:Python运行时加-O(优化模式)会禁用assertAssertionError不会触发。
# 断言条件:参数必须大于0
def func(x):
    assert x > 0, f"参数x必须为正,当前为{x}"  # 条件不满足时触发AssertionError
    return x * 2

try:
    func(-1)
except AssertionError as e:
    print(f"AssertionError: {e}")  # 输出“AssertionError: 参数x必须为正,当前为-1”

3.1.2 AttributeError

  • 触发场景:访问对象不存在的属性(或赋值给不允许赋值的属性,如int__name__)。
# 1. 访问不存在的属性
obj = type("MyClass", (), {"attr1": 1})()  # 自定义类实例,仅含attr1
try:
    print(obj.attr2)  # 访问不存在的attr2
except AttributeError as e:
    print(f"AttributeError: {e}")  # 输出“AttributeError: 'MyClass' object has no attribute 'attr2'”

# 2. 3.10+ 新增name和obj属性,可直接获取出错的属性名和对象
try:
    obj.attr2
except AttributeError as e:
    print(f"属性名:{e.name}, 对象:{e.obj}")  # 输出“属性名:attr2, 对象:<__main__.MyClass object at 0x...>”

3.2 查找相关异常

3.2.1 IndexError

  • 触发场景:序列(如列表、元组)的索引超出范围(切片会静默截断,不会触发)。
lst = [1, 2, 3]
try:
    print(lst[5])  # 索引5超出范围(最大索引为2)
except IndexError as e:
    print(f"IndexError: {e}")  # 输出“IndexError: list index out of range”

# 切片不会触发IndexError(静默截断)
print(lst[5:])  # 输出“[]”,无异常

3.2.2 KeyError

  • 触发场景:字典(或其他映射类型)中查找不存在的键。
d = {"name": "Alice", "age": 25}
try:
    print(d["gender"])  # 查找不存在的键gender
except KeyError as e:
    print(f"KeyError: {e}")  # 输出“KeyError: 'gender'”

# 推荐用get()方法避免KeyError
print(d.get("gender", "未知"))  # 输出“未知”,无异常

3.3 类型与值相关异常

3.3.1 TypeError

  • 触发场景:操作或函数应用于“类型不匹配”的对象(如用整数加字符串、调用非可调用对象)。
# 1. 类型不匹配的运算
try:
    result = 1 + "2"  # 整数 + 字符串,类型不匹配
except TypeError as e:
    print(f"TypeError: {e}")  # 输出“TypeError: unsupported operand type(s) for +: 'int' and 'str'”

# 2. 调用非可调用对象
x = 123  # 整数不可调用
try:
    x()
except TypeError as e:
    print(f"TypeError: {e}")  # 输出“TypeError: 'int' object is not callable”

3.3.2 ValueError

  • 触发场景:参数类型正确,但值不合法(如将非数字字符串转为整数、列表中删除不存在的元素)。
# 1. 类型正确但值不合法的转换
try:
    int("abc")  # 字符串类型正确,但值不是数字
except ValueError as e:
    print(f"ValueError: {e}")  # 输出“ValueError: invalid literal for int() with base 10: 'abc'”

# 2. 列表中删除不存在的元素
lst = [1, 2, 3]
try:
    lst.remove(4)  # 元素4不存在于列表
except ValueError as e:
    print(f"ValueError: {e}")  # 输出“ValueError: list.remove(x): x not in list”

3.4 导入与名称相关异常

3.4.1 ImportErrorModuleNotFoundError(Python 3.6+)

  • ImportError:导入模块失败(如模块内缺少指定名称)。
  • ModuleNotFoundErrorImportError的子类,特指“模块本身不存在”(3.6+新增,更精准)。
# 1. 模块不存在(触发ModuleNotFoundError)
try:
    import non_existent_module  # 模块不存在
except ModuleNotFoundError as e:
    print(f"ModuleNotFoundError: {e}")  # 输出“ModuleNotFoundError: No module named 'non_existent_module'”

# 2. 模块存在但缺少指定名称(触发ImportError)
try:
    from math import non_existent_func  # math模块无此函数
except ImportError as e:
    print(f"ImportError: {e}")  # 输出“ImportError: cannot import name 'non_existent_func' from 'math'”

3.4.2 NameErrorUnboundLocalError

  • NameError:引用未定义的局部或全局名称。
  • UnboundLocalErrorNameError的子类,特指“函数内引用未绑定的局部变量”(如局部变量在赋值前被引用)。
# 1. 引用未定义的全局名称(NameError)
try:
    print(undefined_var)  # undefined_var未定义
except NameError as e:
    print(f"NameError: {e}")  # 输出“NameError: name 'undefined_var' is not defined”

# 2. 函数内引用未绑定的局部变量(UnboundLocalError)
def func():
    print(x)  # 局部变量x在赋值前被引用
    x = 10

try:
    func()
except UnboundLocalError as e:
    print(f"UnboundLocalError: {e}")  # 输出“UnboundLocalError: local variable 'x' referenced before assignment”

3.5 运行时相关异常

3.5.1 RuntimeError

  • 触发场景:捕获到“无法归类到其他异常”的运行时错误(如递归深度超出限制的旧版本、解释器内部错误)。

3.5.2 RecursionError(Python 3.5+)

  • RuntimeError的子类,触发场景:递归调用深度超出Python默认限制(默认约1000层)。
def recursive_func(n):
    if n == 0:
        return
    recursive_func(n - 1)  # 递归调用

try:
    recursive_func(2000)  # 递归深度2000,超出默认限制
except RecursionError as e:
    print(f"RecursionError: {e}")  # 输出“RecursionError: maximum recursion depth exceeded in comparison”

# 可通过sys.setrecursionlimit()调整限制(不建议过大,可能导致栈溢出)
import sys
sys.setrecursionlimit(3000)  # 调整为3000层

3.5.3 NotImplementedError

  • RuntimeError的子类,触发场景:抽象基类的方法要求子类重写,但子类未实现;或功能暂未开发完成。
class BaseService:
    def process(self):
        # 抽象方法,要求子类重写
        raise NotImplementedError("子类必须实现process()方法")

class UserService(BaseService):
    # 未重写process()方法
    pass

try:
    service = UserService()
    service.process()
except NotImplementedError as e:
    print(f"NotImplementedError: {e}")  # 输出“NotImplementedError: 子类必须实现process()方法”

3.6 迭代相关异常

3.6.1 StopIteration

  • 触发场景:迭代器(如生成器、next()函数)无更多元素可返回时触发;生成器返回值时也会触发(返回值作为StopIterationvalue属性)。
# 1. 迭代器耗尽
it = iter([1, 2, 3])
print(next(it))  # 1
print(next(it))  # 2
print(next(it))  # 3
try:
    print(next(it))  # 无更多元素,触发StopIteration
except StopIteration as e:
    print(f"StopIteration: {e.value}")  # 输出“StopIteration: None”(无返回值时value为None)

# 2. 生成器返回值触发StopIteration
def gen():
    yield 1
    yield 2
    return "生成器结束"  # 返回值作为StopIteration的value

g = gen()
print(next(g))  # 1
print(next(g))  # 2
try:
    next(g)
except StopIteration as e:
    print(f"StopIteration value: {e.value}")  # 输出“StopIteration value: 生成器结束”

3.6.2 StopAsyncIteration(Python 3.5+)

  • 触发场景:异步迭代器(async for)无更多元素可返回时触发,用法与StopIteration类似(针对异步场景)。

3.7 系统与内存相关异常

3.7.1 KeyboardInterrupt

  • 触发场景:用户按下中断键(如Ctrl+C),用于终止运行中的程序。
  • 注意:继承自BaseExceptionexcept Exception无法捕获,需显式捕获KeyboardInterrupt
import time

try:
    print("程序运行中,按Ctrl+C终止...")
    while True:
        time.sleep(1)  # 模拟耗时操作
except KeyboardInterrupt:
    print("\n程序被用户中断(Ctrl+C)")  # 捕获Ctrl+C,优雅退出

3.7.2 MemoryError

  • 触发场景:操作耗尽内存且无法通过删除对象挽救时触发(如创建超大列表、处理超大文件)。
  • 注意:Python整数支持任意长度,通常不会因整数过大触发,多发生于大量对象占用内存时。
try:
    # 尝试创建超大列表(约占用4GB内存,视系统内存而定)
    large_list = [0] * (10 ** 9)
except MemoryError as e:
    print(f"MemoryError: {e}")  # 输出“MemoryError:”(部分系统可能无具体信息)

3.7.3 SystemExit

  • 触发场景:调用sys.exit(n)时触发,用于终止程序(n为退出状态码,0表示正常退出)。
  • 注意:继承自BaseExceptionexcept Exception无法捕获,程序退出时默认不打印回溯。

4. OS相关异常(OSError子类)

OSError是系统调用错误的基类,Python 3.3+将IOErrorWindowsError等合并为OSError,并根据系统错误码派生出多个子类,使错误分类更精准。

4.1 文件相关异常

4.1.1 FileNotFoundError

  • 触发场景:操作的文件或目录不存在(如open()不存在的文件、os.remove()不存在的路径)。
try:
    # 打开不存在的文件
    with open("non_existent_file.txt", "r") as f:
        content = f.read()
except FileNotFoundError as e:
    print(f"FileNotFoundError: {e.filename} 不存在")  # 输出“FileNotFoundError: non_existent_file.txt 不存在”

4.1.2 FileExistsError

  • 触发场景:试图创建已存在的文件或目录(如os.mkdir()创建已存在的目录)。
import os

try:
    os.mkdir("test_dir")  # 第一次创建成功
    os.mkdir("test_dir")  # 第二次创建,目录已存在
except FileExistsError as e:
    print(f"FileExistsError: {e.filename} 已存在")  # 输出“FileExistsError: test_dir 已存在”

4.1.3 IsADirectoryErrorNotADirectoryError

  • IsADirectoryError:对目录执行文件操作(如os.remove()删除目录)。
  • NotADirectoryError:对文件执行目录操作(如os.listdir()列出文件的内容)。
import os

# 1. IsADirectoryError:删除目录(需用os.rmdir())
try:
    os.remove("test_dir")  # test_dir是目录,os.remove()用于删除文件
except IsADirectoryError as e:
    print(f"IsADirectoryError: {e.filename} 是目录")  # 输出“IsADirectoryError: test_dir 是目录”

# 2. NotADirectoryError:列出文件的内容(os.listdir()用于目录)
try:
    os.listdir("test_file.txt")  # test_file.txt是文件
except NotADirectoryError as e:
    print(f"NotADirectoryError: {e.filename} 不是目录")  # 输出“NotADirectoryError: test_file.txt 不是目录”

4.2 连接相关异常(ConnectionError子类)

ConnectionError是网络连接错误的基类,子类包括:

  • ConnectionRefusedError:连接被对方拒绝(如目标端口未开放)。
  • ConnectionAbortedError:连接被对方中止(如对方主动关闭连接)。
  • ConnectionResetError:连接被对方重置(如网络中断后对方重启)。
  • BrokenPipeError:写入已关闭的管道或套接字(如对方已断开,仍尝试写入)。
import socket

# 尝试连接未开放的端口(如本地9999端口无服务)
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
try:
    s.connect(("localhost", 9999))
except ConnectionRefusedError as e:
    print(f"ConnectionRefusedError: {e}")  # 输出“ConnectionRefusedError: [Errno 111] Connection refused”
finally:
    s.close()

4.3 权限与进程相关异常

4.3.1 PermissionError

  • 触发场景:操作无足够权限(如写入只读文件、删除系统保护的目录)。
try:
    # 尝试写入只读文件(假设test_readonly.txt权限为只读)
    with open("test_readonly.txt", "w") as f:
        f.write("test")
except PermissionError as e:
    print(f"PermissionError: 无权限操作 {e.filename}")  # 输出“PermissionError: 无权限操作 test_readonly.txt”

4.3.2 ProcessLookupError

  • 触发场景:操作的进程不存在(如os.kill()杀死不存在的进程)。
import os

# 尝试杀死不存在的进程(假设PID 99999无对应进程)
try:
    os.kill(99999, 9)  # 9是SIGKILL信号
except ProcessLookupError as e:
    print(f"ProcessLookupError: 进程 {e.pid} 不存在")  # 输出“ProcessLookupError: 进程 99999 不存在”

4.3.3 TimeoutError(Python 3.3+)

  • 触发场景:系统调用超时(如socket连接超时、os.waitpid()超时)。
import socket

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.settimeout(2)  # 设置超时时间2秒
try:
    # 连接无法访问的IP(如192.168.1.254,无响应)
    s.connect(("192.168.1.254", 80))
except TimeoutError as e:
    print(f"TimeoutError: 连接超时")  # 输出“TimeoutError: timed out”
finally:
    s.close()

5. 警告类别(Warning子类)

警告(Warning)不是错误,用于提示“潜在风险”(如使用已弃用的API、模糊的语法),默认不中断程序运行。需通过warnings模块控制警告的显示(如忽略、转为异常)。

5.1 开发相关警告

5.1.1 DeprecationWarning

  • 用途:提示“API已弃用,供开发者参考”(如旧版本的urllib2模块)。
  • 默认行为:默认被警告过滤器忽略,仅在__main__模块或开发模式(python -X dev)下显示。

5.1.2 PendingDeprecationWarning

  • 用途:提示“API即将弃用,但目前仍可用”(较少使用,通常直接用DeprecationWarning)。

5.2 用户与运行时警告

5.2.1 UserWarning

  • 用途:用户代码自定义的警告(如“输入参数不推荐,建议使用新参数”)。

5.2.2 FutureWarning

  • 用途:提示“API未来行为会改变,供应用用户参考”(如pandas的旧版函数参数)。

5.2.3 RuntimeWarning

  • 用途:提示“运行时的模糊行为”(如整数除以零的浮点数结果inf、无效的复数运算)。
import warnings

# 1. 发出警告
def func(old_param=None, new_param=None):
    if old_param is not None:
        # 发出UserWarning,提示旧参数已不推荐
        warnings.warn(
            "old_param已不推荐使用,请使用new_param",
            UserWarning,
            stacklevel=2  # 正确定位警告的调用栈
        )
    return new_param or old_param

# 2. 控制警告显示(设为“始终显示”)
warnings.simplefilter("always", UserWarning)

# 3. 调用函数触发警告
func(old_param=10)
# 运行结果:
# UserWarning: old_param已不推荐使用,请使用new_param
#   warnings.warn(...)

# 4. 将警告转为异常(用于严格检查)
warnings.simplefilter("error", UserWarning)
try:
    func(old_param=10)
except UserWarning as e:
    print(f"捕获到警告转为的异常:{e}")  # 输出“捕获到警告转为的异常:old_param已不推荐使用,请使用new_param”

5.3 编码与资源警告

  • EncodingWarning(Python 3.10+):提示“编码相关的潜在问题”(如文件编码自动检测不准确)。
  • UnicodeWarning:提示“Unicode相关的潜在问题”(如字节串解码为Unicode时的模糊字符)。
  • ResourceWarning:提示“资源未正确释放”(如文件未关闭、socket未关闭),默认仅在开发模式下显示。

6. 异常组(Python 3.11+)

Python 3.11+ 引入异常组BaseExceptionGroupExceptionGroup),用于一次性引发多个不相关的异常(如并行任务中的多个错误),并通过except*语法精准捕获。

6.1 核心概念

  • BaseExceptionGroup:继承自BaseException,可包装任意异常(包括系统级异常如KeyboardInterrupt)。
  • ExceptionGroup:继承自Exception,仅可包装Exception的子类(应用级异常),构造器若传入非Exception子类会触发TypeError
  • 关键属性
    • message:异常组的描述信息(如“并行任务中的多个错误”)。
    • exceptions:包装的异常元组。

6.2 引发与捕获异常组

# 1. 引发ExceptionGroup(仅包装应用级异常)
try:
    raise ExceptionGroup(
        "批量处理数据时的错误",  # message
        [
            ValueError("数据1格式无效"),
            KeyError("数据2缺少关键字段"),
            TypeError("数据3类型不匹配")
        ]
    )
except* ValueError as eg:
    # 捕获异常组中所有ValueError
    print(f"捕获到ValueError异常组:{eg.message}")
    for e in eg.exceptions:
        print(f"- {e}")  # 输出“- 数据1格式无效”
except* (KeyError, TypeError) as eg:
    # 捕获异常组中所有KeyError和TypeError
    print(f"\n捕获到KeyError/TypeError异常组:{eg.message}")
    for e in eg.exceptions:
        print(f"- {type(e).__name__}: {e}")  # 输出“- KeyError: 数据2缺少关键字段”和“- TypeError: 数据3类型不匹配”

# 2. 引发BaseExceptionGroup(可包装系统级异常)
try:
    raise BaseExceptionGroup(
        "包含系统级异常的组",
        [
            ValueError("应用错误"),
            KeyboardInterrupt("用户中断")  # 系统级异常
        ]
    )
except* Exception as eg:
    # 仅捕获应用级异常(ValueError),KeyboardInterrupt不会被捕获
    print(f"\n捕获到应用级异常组:{eg.exceptions}")  # 输出“捕获到应用级异常组:(ValueError('应用错误'),)”

为方便查阅,以下是Python内置异常的核心继承关系(精简版):

BaseException
├── BaseExceptionGroup       # 异常组(Python 3.11+)
├── GeneratorExit            # 生成器关闭时触发
├── KeyboardInterrupt        # 用户中断(Ctrl+C)
├── SystemExit               # 程序退出(sys.exit())
└── Exception                # 应用级异常基类
    ├── ArithmeticError      # 算术错误基类
    │   ├── FloatingPointError  # 浮点运算错误(极少用)
    │   ├── OverflowError    # 数值溢出(极少用)
    │   └── ZeroDivisionError  # 除以零
    ├── AssertionError       # assert语句失败
    ├── AttributeError       # 访问不存在的属性
    ├── BufferError          # 缓冲区操作错误
    ├── EOFError             # 输入到达EOF无数据
    ├── ExceptionGroup       # 应用级异常组(Python 3.11+)
    ├── ImportError          # 导入错误
    │   └── ModuleNotFoundError  # 模块不存在(Python 3.6+)
    ├── LookupError          # 查找错误基类
    │   ├── IndexError       # 序列索引超出范围
    │   └── KeyError         # 映射键不存在
    ├── MemoryError          # 内存耗尽
    ├── NameError            # 名称未定义
    │   └── UnboundLocalError  # 局部变量未绑定
    ├── OSError              # 系统错误基类
    │   ├── BlockingIOError  # 非阻塞操作阻塞
    │   ├── ChildProcessError  # 子进程操作失败
    │   ├── ConnectionError  # 连接错误基类
    │   │   ├── BrokenPipeError  # 管道已关闭仍写入
    │   │   ├── ConnectionAbortedError  # 连接被中止
    │   │   ├── ConnectionRefusedError  # 连接被拒绝
    │   │   └── ConnectionResetError  # 连接被重置
    │   ├── FileExistsError  # 创建已存在的文件/目录
    │   ├── FileNotFoundError  # 文件/目录不存在
    │   ├── InterruptedError  # 系统调用被信号中断
    │   ├── IsADirectoryError  # 对目录执行文件操作
    │   ├── NotADirectoryError  # 对文件执行目录操作
    │   ├── PermissionError  # 权限不足
    │   ├── ProcessLookupError  # 进程不存在
    │   └── TimeoutError     # 系统调用超时(Python 3.3+)
    ├── ReferenceError       # 弱引用访问已回收对象
    ├── RuntimeError         # 未归类的运行时错误
    │   ├── NotImplementedError  # 方法未实现
    │   ├── PythonFinalizationError  # 解释器终结时操作被阻止(Python 3.13+)
    │   └── RecursionError   # 递归深度超出限制(Python 3.5+)
    ├── StopAsyncIteration   # 异步迭代器结束(Python 3.5+)
    ├── StopIteration        # 迭代器结束
    ├── SyntaxError          # 语法错误
    │   └── IndentationError  # 缩进错误
    │       └── TabError     # 制表符与空格混用
    ├── SystemError          # 解释器内部错误
    ├── TypeError            # 类型不匹配
    ├── ValueError           # 值不合法
    │   └── UnicodeError     # Unicode编码/解码错误
    │       ├── UnicodeDecodeError  # 解码错误
    │       ├── UnicodeEncodeError  # 编码错误
    │       └── UnicodeTranslateError  # 转写错误
    └── Warning              # 警告基类
        ├── BytesWarning     # bytes/bytearray相关警告
        ├── DeprecationWarning  # API已弃用(开发者参考)
        ├── EncodingWarning  # 编码相关警告(Python 3.10+)
        ├── FutureWarning    # API未来行为改变(用户参考)
        ├── ImportWarning    # 导入相关警告
        ├── PendingDeprecationWarning  # API即将弃用
        ├── ResourceWarning  # 资源未正确释放
        ├── RuntimeWarning   # 运行时模糊行为
        ├── SyntaxWarning    # 语法模糊
        ├── UnicodeWarning   # Unicode相关警告
        └── UserWarning      # 用户自定义警告

7. 总结

  1. 精准捕获:避免用except Exception捕获所有异常,应针对性捕获具体异常(如except ValueError),防止掩盖系统级异常(如KeyboardInterrupt)。
  2. 异常上下文:使用raise new_exc from original_exc显式关联异常原因,帮助调试时追溯完整错误链。
  3. 自定义异常:继承Exception而非BaseException,并通过子类细化错误类型(如ConfigErrorConfigNotFoundError)。
  4. 版本兼容:注意新增异常的版本(如ExceptionGroup在Python 3.11+),避免在低版本环境中使用。
Logo

Agent 垂直技术社区,欢迎活跃、内容共建。

更多推荐