对象生命周期
| __new__(cls, …) | 创建实例时 | 新实例 | 类的构造器,在 __init__ 之前调用 |
| __init__(self, …) | 实例创建后 | None | 初始化实例,接收构造器参数 |
| __del__(self) | 垃圾回收时 | None | 析构器,通常不推荐手动实现 |
示例:
class MyClass:
def __new__(cls, *args, **kwargs):
print(f"__new__ called for {cls}")
return super().__new__(cls)
def __init__(self, value):
print(f"__init__ called with {value}")
self.value = value
def __del__(self):
print(f"__del__ called for {self}")
对象表示
| __str__(self) | str(obj) / print(obj) | 字符串 | 对象的友好字符串表示 |
| __repr__(self) | repr(obj) / REPL | 字符串 | 对象的开发者友好表示,通常可用来重建对象 |
| __format__(self, format_spec) | format(obj, spec) / f-string | 字符串 | 格式化输出 |
| __bytes__(self) | bytes(obj) | bytes | 字节表示 |
示例:
class Point:
def __init__(self, x, y):
self.x = x
self.y = y
def __str__(self):
return f"Point({self.x}, {self.y})"
def __repr__(self):
return f"Point(x={self.x}, y={self.y})"
def __format__(self, format_spec):
return f"<{self.x}, {self.y}>"
p = Point(3, 4)
print(p) # Point(3, 4) – __str__
print(repr(p) ) # Point(x=3, y=4) – __repr__
print(f"{p}" ) # Point(3, 4) – 默认使用 __str__
比较操作
| __lt__(self, other) | < | bool | 小于 |
| __le__(self, other) | <= | bool | 小于等于 |
| __eq__(self, other) | == | bool | 等于 |
| __ne__(self, other) | != | bool | 不等于 |
| __gt__(self, other) | > | bool | 大于 |
| __ge__(self, other) | >= | bool | 大于等于 |
使用 @functools.total_ordering 简化:
from functools import total_ordering
@total_ordering
class Person:
def __init__(self, age):
self.age = age
def __eq__(self, other):
if not isinstance(other, Person):
return NotImplemented
return self.age == other.age
def __lt__(self, other):
if not isinstance(other, Person):
return NotImplemented
return self.age < other.age
容器类型
容器大小与成员检测
| __len__(self) | len(obj) | 整数 | 容器长度 |
| __bool__(self) | bool(obj) | bool | 真值测试 |
| __contains__(self, item) | item in obj | bool | 成员测试 |
| __iter__(self) | iter(obj) | 迭代器 | 返回迭代器对象 |
元素访问
| __getitem__(self, key) | obj[key] | 任意值 | 获取元素 |
| __setitem__(self, key, value) | obj[key] = value | None | 设置元素 |
| __delitem__(self, key) | del obj[key] | None | 删除元素 |
| __missing__(self, key) | key 不存在时 | 任意值 | dict 子类的 fallback |
示例:自定义列表:
class CustomList:
def __init__(self, items=None):
self._items = items or []
def __len__(self):
return len(self._items)
def __getitem__(self, index):
return self._items[index]
def __setitem__(self, index, value):
self._items[index] = value
def __delitem__(self, index):
del self._items[index]
def __contains__(self, item):
return item in self._items
def __iter__(self):
return iter(self._items)
可调用对象
| __call__(self, *args, **kwargs) | obj() | 任意值 | 使对象像函数一样可调用 |
示例:
class Adder:
def __init__(self, n):
self.n = n
def __call__(self, x):
return self.n + x
add5 = Adder(5)
add5(10) # 返回 15
上下文管理
| __enter__(self) | with 块进入时 | 任意值 | 通常返回 self 或资源 |
| __exit__(self, exc_type, exc_val, exc_tb) | with 块退出时 | bool/None | 清理资源,可处理异常 |
示例:
class FileContext:
def __init__(self, filename, mode):
self.filename = filename
self.mode = mode
def __enter__(self):
self.file = open(self.filename, self.mode)
return self.file
def __exit__(self, exc_type, exc_val, exc_tb):
self.file.close()
return False # 不抑制异常
with FileContext('test.txt', 'w') as f:
f.write('Hello')
迭代器协议
| __iter__(self) | iter(obj) / for 循环 | 迭代器 | 返回自身(如果是迭代器) |
| __next__(self) | next(iterator) | 任意值 | 返回下一个元素,无元素时抛出 StopIteration |
示例:自定义迭代器:
class CountDown:
def __init__(self, start):
self.current = start
def __iter__(self):
return self
def __next__(self):
if self.current <= 0:
raise StopIteration
self.current -= 1
return self.current + 1
for i in CountDown(5):
print(i) # 输出: 5, 4, 3, 2, 1
数值运算
一元运算
| __neg__(self) | -obj | 数值 | 负号 |
| __pos__(self) | +obj | 数值 | 正号 |
| __abs__(self) | abs(obj) | 数值 | 绝对值 |
| __invert__(self) | ~obj | 数值 | 按位取反 |
二元运算
| __add__(self, other) | + | 数值 | 加法 |
| __sub__(self, other) | – | 数值 | 减法 |
| __mul__(self, other) | * | 数值 | 乘法 |
| __truediv__(self, other) | / | 数值 | 真除法 |
| __floordiv__(self, other) | // | 数值 | 地板除 |
| __mod__(self, other) | % | 数值 | 取模 |
| __pow__(self, other, modulo) | ** / pow() | 数值 | 幂运算 |
| __divmod__(self, other) | divmod() | 元组 | 商和余数 |
位运算
| __and__(self, other) | & | 数值 | 按位与 |
| __or__(self, other) | | | 数值 | 按位或 |
| __xor__(self, other) | ^ | 数值 | 按位异或 |
| __lshift__(self, other) | << | 数值 | 左移 |
| __rshift__(self, other) | >> | 数值 | 右移 |
反向运算(右操作数类型不匹配时)
| __radd__(self, other) | a + b 当 a 不支持 + 且 b 定义时 | |
| __rsub__(self, other) | a – b 的反向 | |
| __rmul__(self, other) | a * b 的反向 | |
| __rtruediv__(self, other) | a / b 的反向 | |
| … | 其他运算符同理 |
增量赋值
| __iadd__(self, other) | += | 任意值 | 原地加法 |
| __isub__(self, other) | -= | 任意值 | 原地减法 |
| __imul__(self, other) | *= | 任意值 | 原地乘法 |
| … | 其他运算符同理 |
示例:复数实现:
class Complex:
def __init__(self, real, imag):
self.real = real
self.imag = imag
def __add__(self, other):
return Complex(self.real + other.real, self.imag + other.imag)
def __mul__(self, other):
return Complex(
self.real * other.real – self.imag * other.imag,
self.real * other.imag + self.imag * other.real
)
def __repr__(self):
return f"Complex({self.real}, {self.imag})"
类型转换
| __int__(self) | int(obj) | 整数 | 转为整数 |
| __float__(self) | float(obj) | 浮点数 | 转为浮点数 |
| __complex__(self) | complex(obj) | 复数 | 转为复数 |
| __index__(self) | hex()/oct()/切片索引 | 整数 | 整数索引协议 |
| __hash__(self) | hash(obj) / 字典键 | 整数 | 哈希值 |
示例:
class Number:
def __init__(self, value):
self.value = value
def __int__(self):
return int(self.value)
def __float__(self):
return float(self.value)
def __hash__(self):
return hash(self.value)
num = Number(3.14)
int(num) # 3
float(num) # 3.14
属性访问
| __getattr__(self, name) | 属性不存在时 | 任意值 | 动态属性访问 |
| __getattribute__(self, name) | 任何属性访问时 | 任意值 | 属性访问拦截(慎用) |
| __setattr__(self, name, value) | 设置属性时 | None | 拦截属性赋值 |
| __delattr__(self, name) | 删除属性时 | None | 拦截属性删除 |
| __dir__(self) | dir(obj) | 列表 | 返回属性列表 |
示例:动态属性:
class DynamicAttrs:
def __init__(self):
self._data = {}
def __getattr__(self, name):
if name in self._data:
return self._data[name]
raise AttributeError(f"'{self.__class__.__name__}' object has no attribute '{name}'")
def __setattr__(self, name, value):
if name.startswith('_'):
super().__setattr__(name, value)
else:
self._data[name] = value
obj = DynamicAttrs()
obj.name = "Alice"
print(obj.name) # Alice
序列协议
| __reversed__(self) | reversed(obj) | 反向迭代器 | 反向遍历 |
示例:
class CountUp:
def __init__(self, max_val):
self.max_val = max_val
def __reversed__(self):
return iter(range(self.max_val, -1, -1))
list(reversed(CountUp(5))) # [5, 4, 3, 2, 1, 0]
核心设计原则
1. NotImplemented vs TypeError
def __eq__(self, other):
if isinstance(other, self.__class__):
return self.value == other.value
return NotImplemented # 让 Python 尝试 other.__eq__(self)
2. 避免无限递归
# ❌ 错误:递归
def __getattr__(self, name):
return self.name # 会再次触发 __getattr__
# ✅ 正确
def __getattr__(self, name):
return self._data[name]
3. __hash__ 与 __eq__ 的一致性
class Person:
def __init__(self, id):
self.id = id
def __eq__(self, other):
return self.id == other.id
def __hash__(self):
return hash(self.id) # 相等的对象必须有相等的 hash
常用组合示例
自定义字典(完整实现)
class CaseInsensitiveDict(dict):
def __setitem__(self, key, value):
super().__setitem__(key.lower(), value)
def __getitem__(self, key):
return super().__getitem__(key.lower())
def __contains__(self, key):
return super().__contains__(key.lower())
d = CaseInsensitiveDict()
d['Name'] = 'Alice'
print(d['name']) # Alice
范围对象(可切片)
class Range:
def __init__(self, start, end=None, step=1):
if end is None:
end = start
start = 0
self.start = start
self.end = end
self.step = step
def __len__(self):
return max(0, (self.end – self.start + self.step – 1) // self.step)
def __getitem__(self, index):
if isinstance(index, slice):
start, stop, step = index.indices(len(self))
return Range(self.start + start * self.step,
self.start + stop * self.step,
self.step * step)
if index < 0:
index += len(self)
if index < 0 or index >= len(self):
raise IndexError("range index out of range")
return self.start + index * self.step
def __iter__(self):
return iter(self[i] for i in range(len(self)))
list(Range(10)[2:7:2]) # [2, 4, 6]
实践建议
参考资料
- Python Data Model – Python 官方文档
- Python Tricks: The Book – Dan Bader




