21_python基础—单例和 __ new __ 方法
文章目录
- 目标
- 一、单例设计模式
- 1.1 设计模式
- 1.2 单例设计模式的应用场景
- 二、 `__new__` 方法
- 2.1 `__new__`方法作用
- 2.2 示例代码
- 三、Python 中的单例
- 3.1 只执行一次初始化工作
目标
- 单例设计模式
__new__
方法- Python 中的单例
一、单例设计模式
1.1 设计模式
- 设计模式
- 设计模式 是 前人工作的总结和提炼,通常,被人们广泛流传的设计模式都是针对 某一特定问题 的成熟的解决方案
- 使用 设计模式 是为了可重用代码、让代码更容易被他人理解、保证代码可靠性
- 单例设计模式
- 目的 —— 让 类 创建的对象,在系统中 只有 唯一的一个实例
- 每一次执行
类名()
返回的对象,内存地址是相同的
1.2 单例设计模式的应用场景
- 音乐播放 对象
- 回收站 对象
- 打印机 对象
- ……
二、 __new__
方法
2.1 __new__
方法作用
使用 类名() 创建对象时,
Python
的解释器 首先 会 调用__new__
方法为对象 分配空间__new__
是一个 由object
基类提供的 内置的静态方法,主要作用有两个:在内存中为对象 分配空间
返回 对象的引用
Python
的解释器获得对象的 引用 后,将引用作为 第一个参数,传递给__init__
方法
写
__new__
方法 的代码非常固定!
2.2 示例代码
class MusicPlayer(object):def __new__(cls, *args, **kwargs):# 1. 创建对象时,new方法会被自动调用print("创建对象,分配空间") # 覆盖了父类方法实现# 2. 为对象分配空间instance = super().__new__(cls)# 3. 返回对象的引用,给python解释器return instancedef __init__(self):print("播放器初始化")# 创建播放器对象
player = MusicPlayer()print(player)
创建对象,分配空间
播放器初始化
<main.MusicPlayer object at 0x000001FEB7F623C8>
- 重写
__new__
方法 一定要return super().__new__(cls)
- 否则 Python 的解释器 得不到 分配了空间的 对象引用,就不会调用对象的初始化方法
- 注意:
__new__
是一个静态方法,在调用时需要 主动传递cls
参数
三、Python 中的单例
- 单例 —— 让 类 创建的对象,在系统中 只有 唯一的一个实例
- 定义一个 类属性,初始值是
None
,用于记录 单例对象的引用 - 重写
__new__
方法 - 如果 类属性
is None
,调用父类方法分配空间,并在类属性中记录结果 - 返回 类属性 中记录的 对象引用
class MusicPlayer(object):# 记录第一个被创建对象的引用instance = Nonedef __new__(cls, *args, **kwargs):# 1. 判断类属性是否是空对象;如果是空对象,说明第一个对象还没有被创建if cls.instance is None:# 2. 如果第一个对象没创建,调用父类的方法,为第一个对象分配空间==>才能用类属性进行记录cls.instance = super().__new__(cls)# 3. 返回类属性保存的对象引用return cls.instance# 创建对象
player = MusicPlayer()
print(player)
<main.MusicPlayer object at 0x00000253D38423C8>
3.1 只执行一次初始化工作
在每次使用
类名()
创建对象时,Python
的解释器都会自动调用两个方法:__new__
分配空间
__init__
对象初始化在上一小节对
__new__
方法改造之后,每次都会得到 第一次被创建对象的引用但是:初始化方法还会被再次调用
需求
- 让 初始化动作 只被 执行一次
解决办法
- 定义一个类属性
init_flag
标记是否 执行过初始化动作,初始值为False
- 在
__init__
方法中,判断init_flag
,如果为False
就执行初始化动作 - 然后将
init_flag
设置为True
- 这样,再次 自动 调用
__init__
方法时,初始化动作就不会被再次执行 了
class MusicPlayer(object):# 记录第一个被创建对象的引用instance = None# 记录是否执行过初始化动作(重要)init_flag = Falsedef __new__(cls, *args, **kwargs):# 1. 判断类属性是否是空对象if cls.instance is None:# 2. 调用父类的方法,为第一个对象分配空间cls.instance = super().__new__(cls)# 3. 返回类属性保存的对象引用return cls.instancedef __init__(self):# 1. 判断是否执行过初始化动作if MusicPlayer.init_flag: # 判断类属性return# 2. 如果没有执行过,在执行初始化动作print("初始化播放器")# 3. 修改类属性的标记MusicPlayer.init_flag = True# 创建多个对象
player1 = MusicPlayer()
print(player1)player2 = MusicPlayer()
print(player2)
初始化播放器
<main.MusicPlayer object at 0x0000015A111219B0>
<main.MusicPlayer object at 0x0000015A111219B0>
提示:初始化执行完成,类属性标记就被设置为真,下一次再次调用初始化方法的时候,类属性标记为真就直接返回,而不会执行下方的初始化动作。
21_python基础—单例和 __ new __ 方法相关推荐
- Java查漏补缺(08)关键字:static、单例设计模式、理解main方法、类的成员之四:代码块、final关键字、抽象类、接口、内部类、枚举类、注解、包装类
Java查漏补缺(08)关键字:static.单例设计模式.理解main方法.类的成员之四:代码块.final关键字.抽象类.接口.内部类.枚举类.注解.包装类 本章专题与脉络 1. 关键字:stat ...
- java单例的几种实现方法
java单例的几种实现方法: 方式1: public class Something { private Something() {}private static class LazyHolder { ...
- was修改类加载模式_java基础——单例(Singleton)模式介绍
基本概括 详解 一.单例模式定义: 单例模式确保某个类只有一个实例,而且自行实例化并向整个系统提供这个实例. 二.单例模式特点: 1.单例类只能有一个实例. 2.单例类必须自己创建自己的唯一实例. 3 ...
- 【Java】day9--main方法、单例设计模式、继承、方法重写部分知识点总结
(一)main方法 jvm调用main方法,jvm也是一个程序 main方法详解: public:公共 保证该类在任何情况下,jvm都对其方法可见. stat ...
- Java基础 - 单例(饿汉、懒汉),2年以上经验必看
//r.exec("shutdown -s -t 300"); //300秒后关机r.exec("shutdown -a"); ``` 3.Timer(掌握) ...
- Java基础学习系列--(二)【抽象类,接口、代码块、final、单例、枚举】
第一章 抽象类 1.1 概述 1.1.1 抽象类引入 父类中的方法,被它的子类们重写,子类各自的实现都不尽相同.那么父类的方法声明和方法主体,只有声明还有意义,而方法主体则没有存在的意义了(因为子类对 ...
- Java(基础)单例(Singleton)
设计模式是在大量的实践中总结和理论化之后优选的代码结构.编程风格. 以及解决问题的思考方式.设计模免去我们自己再思考和摸索.就像是经典 的棋谱,不同的棋局,我们用不同的棋谱."套路" ...
- Spring IOC 容器源码分析 - 创建单例 bean 的过程
1. 简介 在上一篇文章中,我比较详细的分析了获取 bean 的方法,也就是getBean(String)的实现逻辑.对于已实例化好的单例 bean,getBean(String) 方法并不会再一次去 ...
- day02-抽象类,接口、代码块、final、单例、枚举
java基础[抽象类,接口.代码块.final.单例.枚举] 第一章 抽象类 1.1 概述 1.1.1 抽象类引入 父类中的方法,被它的子类们重写,子类各自的实现都不尽相同.那么父类的方法声明和方法主 ...
最新文章
- 设计模式我学过呀,就是没用过
- linux命令安装openssl函数库,ubuntu安装openssl库
- 6.SQL Server Sql语句
- asch相关的linux基础知识分享
- r语言中矩阵QR分解_从零开始学R语言Day4|向量、矩阵和数组
- jdbc,mybatis,hibernate各自优缺点及区别
- ***是如何能破解诸如美国中情局之类的密码
- 手机调试_手机充值不好用?因为正在调试期
- JDK11+Tomcat10 下载安装+环境配置
- Atitit sql执行计划
- Dagger 2 系列(一) -- 前奏篇:依赖注入的基本介绍
- ubuntu下Qt cannot find -lGL错误的解决方法
- 【图像去噪】基于matlab GUI均值+中值+高通低通+巴特沃斯+PCA+小波+维纳滤波图像去噪【含Matlab源码 1705期】
- linux密码忘记重新设置密码
- 基于STM32的MLX90614(GY-906)人体红外测温
- CentOs下安装pip3
- android 自定义数字软键盘,(笔记)Android自定义数字键盘
- Gym - 101177K Kiwis vs Kangaroos 水题手动打表
- 电流输入放大器的设计
- 小程序中如何关注公众号
热门文章
- C语言课后习题(20)
- MySQL 8.0 表空间机制
- DBA邀请函丨数据库大咖讲坛来深圳啦!线下沙龙+线上直播,共享技术盛会!
- 二月技术通讯.pdf丨核心数据库一波三折异常重启分析
- 每周精选:20万DBA都在关注的11个问题
- 一文了解GaussDB 200的产品架构、数据流程、组网方案、服务部署原则、企业级增强特性......
- 解析HetuEngine实现On Yarn原理
- 深度学习分类任务常用评估指标
- 用好CloudIDE提升Web全栈编码效率
- 安全性能两手抓,华为云MySQL“非双一特性”助力企业业务稳定高效运行