0

0

Python 魔术方法与面向对象设计的结合

舞夢輝影

舞夢輝影

发布时间:2026-01-29 17:02:02

|

370人浏览过

|

来源于php中文网

原创

真正影响对象生命周期的魔术方法是__new__、__enter__、__exit__和__del__;其中__enter__/__exit__是资源清理的可靠入口,__new__用于实例化前控制,__del__不保证执行时机。

python 魔术方法与面向对象设计的结合

__init__ 之外,哪些魔术方法真正影响对象生命周期

对象创建后立刻被销毁、或在上下文管理中意外中断,往往不是逻辑错误,而是没补全关键魔术方法。比如 __del__ 并不保证执行时机,而 __enter____exit__ 才是资源清理的可靠入口。

常见错误现象:ResourceWarning: unclosed file 或数据库连接泄漏,多数因只写了 __init__ 分配资源,却没配对实现上下文协议。

  • __new__ 在实例化前介入,适合单例、类型控制(如返回子类实例),但别在里面做耗时操作
  • __del__ 不要依赖它释放关键资源;它可能在解释器关闭时才触发,甚至不触发
  • 若对象需自动释放(文件、锁、网络连接),必须同时实现 __enter____exit__,且 __exit__ 要显式处理异常传播(返回 True 表示吞掉异常)

__eq__ 和 __hash__ 不配对会导致字典/集合行为异常

自定义类放进 set 或作为 dict 键时突然“消失”或重复,大概率是重写了 __eq__ 却忘了同步调整 __hash__

Python 规则很硬:只要 __eq__ 被重写,默认 __hash__ 就设为 None,导致实例不可哈希——此时往 set 里加会报 TypeError: unhashable type

立即学习Python免费学习笔记(深入)”;

citySHOP多用户商城系统
citySHOP多用户商城系统

citySHOP是一款集CMS、网店、商品、分类信息、论坛等为一体的城市多用户商城系统,已完美整合目前流行的Discuz! 6.0论坛,采用最新的5.0版PHP+MYSQL技术。面向对象的数据库连接机制,缓存及80%静态化处理,使它能最大程度减轻服务器负担,为您节约建设成本。多级店铺区分及联盟商户地图标注,实体店与虚拟完美结合。个性化的店铺系统,会员后台一体化管理。后台登陆初始网站密匙:LOVES

下载
  • 若对象逻辑上“可变”,应显式设 __hash__ = None,避免误用
  • 若对象逻辑“不可变”(如坐标点、配置项),__hash__ 应基于参与 __eq__ 判等的字段计算,例如 return hash((self.x, self.y))
  • 注意浮点字段慎入 __hash__float('nan') 的哈希值未定义,会导致集合操作崩溃

__str__ vs __repr__ 混用会干扰调试和日志可读性

日志里打印出一串 <__main__.dataobject object at>,或者 REPL 中显示一堆无意义字符串,说明这两个方法没按角色分工。

__repr__ 是给开发者看的,目标是“能还原对象”;__str__ 是给用户看的,目标是“好读”。两者输出差异太大,会导致调试时信息缺失,太小又让终端输出难理解。

  • __repr__ 应包含类名和关键属性,格式尽量接近构造调用,例如 DataPoint(x=1.2, y=3.4)
  • __str__ 可简化,甚至返回自然语言描述,例如 "Point at (1.2, 3.4)"
  • 如果类没有业务含义(如纯数据容器),可直接让 __str__ = __repr__,但别反过来

__getattr__ 和 __getattribute__ 选错会引发无限递归

一加 __getattr__ 就报 RecursionError: maximum recursion depth exceeded,通常是误用了 __getattribute__,或在其中访问了自身属性。

区别很关键:__getattribute__ 拦截所有属性访问(包括 __dict__、方法),而 __getattr__ 只在属性查找不到时才触发。

  • 想做“属性代理”或“动态字段 fallback”,优先用 __getattr__,安全且轻量
  • 非要用 __getattribute__(比如统一审计字段访问),必须用 super().__getattribute__(name) 获取原始值,绝不能直接写 self.xxx
  • __getattr__ 里抛异常时,别再触发自己——例如访问 self.__dict__ 是安全的,但 self.some_missing_attr 会再次进 __getattr__
实际项目里,最常被忽略的是 __hash____eq__ 的绑定关系,以及 __getattribute__ 中绕过父类访问的写法。这两处一旦出错,问题往往延迟暴露,排查成本远高于初期多写两行。

热门AI工具

更多
DeepSeek
DeepSeek

幻方量化公司旗下的开源大模型平台

豆包大模型
豆包大模型

字节跳动自主研发的一系列大型语言模型

通义千问
通义千问

阿里巴巴推出的全能AI助手

腾讯元宝
腾讯元宝

腾讯混元平台推出的AI助手

文心一言
文心一言

文心一言是百度开发的AI聊天机器人,通过对话可以生成各种形式的内容。

讯飞写作
讯飞写作

基于讯飞星火大模型的AI写作工具,可以快速生成新闻稿件、品宣文案、工作总结、心得体会等各种文文稿

即梦AI
即梦AI

一站式AI创作平台,免费AI图片和视频生成。

ChatGPT
ChatGPT

最最强大的AI聊天机器人程序,ChatGPT不单是聊天机器人,还能进行撰写邮件、视频脚本、文案、翻译、代码等任务。

相关专题

更多
css中float用法
css中float用法

css中float属性允许元素脱离文档流并沿其父元素边缘排列,用于创建并排列、对齐文本图像、浮动菜单边栏和重叠元素。想了解更多float的相关内容,可以阅读本专题下面的文章。

579

2024.04.28

C++中int、float和double的区别
C++中int、float和double的区别

本专题整合了c++中int和double的区别,阅读专题下面的文章了解更多详细内容。

102

2025.10.23

go语言 面向对象
go语言 面向对象

本专题整合了go语言面向对象相关内容,阅读专题下面的文章了解更多详细内容。

56

2025.09.05

java面向对象
java面向对象

本专题整合了java面向对象相关内容,阅读专题下面的文章了解更多详细内容。

52

2025.11.27

go语言 面向对象
go语言 面向对象

本专题整合了go语言面向对象相关内容,阅读专题下面的文章了解更多详细内容。

56

2025.09.05

java面向对象
java面向对象

本专题整合了java面向对象相关内容,阅读专题下面的文章了解更多详细内容。

52

2025.11.27

go语言 面向对象
go语言 面向对象

本专题整合了go语言面向对象相关内容,阅读专题下面的文章了解更多详细内容。

56

2025.09.05

java面向对象
java面向对象

本专题整合了java面向对象相关内容,阅读专题下面的文章了解更多详细内容。

52

2025.11.27

clawdbot ai使用教程 保姆级clawdbot部署安装手册
clawdbot ai使用教程 保姆级clawdbot部署安装手册

Clawdbot是一个“有灵魂”的AI助手,可以帮用户清空收件箱、发送电子邮件、管理日历、办理航班值机等等,并且可以接入用户常用的任何聊天APP,所有的操作均可通过WhatsApp、Telegram等平台完成,用户只需通过对话,就能操控设备自动执行各类任务。

14

2026.01.29

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
最新Python教程 从入门到精通
最新Python教程 从入门到精通

共4课时 | 22.4万人学习

Django 教程
Django 教程

共28课时 | 3.6万人学习

SciPy 教程
SciPy 教程

共10课时 | 1.3万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号