python单例和工厂模式

设计模式

设计模式是一种编程套路,可以极大的方便程序的开发

最常见、最经典的设计模式,就是学习的面向对象

除了面向对象之外,在编程中也有很多既定的套路可以方便开发,我们称之为设计模式:

  • 单例、工厂模式
  • 建造者、责任链、状态、备忘录、解释器、访问者、观察者、中介、模板、代理模式
  • 等等模式
单例模式

创建类的实例后,可以得到一个完整的、独立的类对象

python 复制代码
class Test:
    pass


t1 = Test()
t2 = Test()
print(t1)
print(t2)

打印的内存地址如下:

powershell 复制代码
<__main__.Test object at 0x0129E718>
<__main__.Test object at 0x0129E628>

发现两个内存地址是不同的,即t1和t2是两个独立的对象

某些场景下,我们需要一个类无论获取多少次类对象,都仅仅提供一个具体的实例

用以节省创建类对象的开销和内存开销

比如某些工具类,仅需一个实例,即可在各处使用

这就是单例模式所要实现的效果

使用模块方式实现单例模式

python 复制代码
class Singleton:
    def call(self):
        pass


singleton = Singleton()
python 复制代码
from Singleton import singleton
s1 = singleton
s2 = singleton
print(s1)
print(s2)

输出结果

powershell 复制代码
<Singleton.Singleton object at 0x0201E388>
<Singleton.Singleton object at 0x0201E388>

两个对象的内存地址相同

使用装饰器实现单例

python 复制代码
def singleton(cls):
    instance = {}

    def _singleton(*args, **kwargs):
        if cls not in instance:
            instance[cls] = cls(*args, **kwargs)
        return instance[cls]

    return _singleton


@singleton
class Animal(object):
    pass


if __name__ == '__main__':
    a1 = Animal()
    a2 = Animal()
    print(a1)
    print(a2)

输出结果

powershell 复制代码
<__main__.Animal object at 0x01D80E98>
<__main__.Animal object at 0x01D80E98>

两个对象的内存地址相同

使用实例化方式实现单例

在‌Python中,call()是一个特殊方法,用于将一个类的实例变成一个可调用对象。

python 复制代码
class Singleton:
    def __call__(self, *args, **kwargs):
        return self


if __name__ == '__main__':
    sin = Singleton()
    s1 = sin()
    s2 = sin()
    print(s1)
    print(s2)

输出结果

powershell 复制代码
<__main__.Singleton object at 0x01CCE718>
<__main__.Singleton object at 0x01CCE718>

两个对象的内存地址相同

工厂模式

当需要大量创建一个类的实例的时候,可以使用工厂模式

从原生的使用类的构造去创建对象的形式迁移到基于工厂提供的方法去创建对象的形式

使用工厂类的get_person()方法去创建具体的类对象

优点:

  • 大批量创建对象的时候有统一的入口,易于代码维护
  • 当发生修改,仅修改工厂类的创建方法即可
  • 符合现实世界的模式,即由工厂来制作产品(对象)
相关推荐
xcLeigh10 小时前
编程语言的 AI 友好度排名:Python、JavaScript、TypeScript 谁更适合 AI 辅助
javascript·人工智能·python·ai·typescript·ai编程
Albart57510 小时前
【已解决】ModuleNotFoundError_ No module named ‘xxx’ 模块导入失败终极解决
python·pip·环境配置·后端开发·bug解决·模块报错·python导包失败
Dr.kangder10 小时前
嵌入式总线设备解析——TTE总线应用与实践
开发语言·网络·算法·嵌入式·多任务·同步机制
-银雾鸢尾-10 小时前
C#中的多线程
开发语言·c#
2401_8582861111 小时前
OS82.【Linux】设计线程池
java·linux·运维·服务器·开发语言·算法·线程池
数据知道11 小时前
IDOR 不安全的直接对象引用:API 越权实战检测
java·开发语言·网络·安全·网络安全
花酒锄作田11 小时前
Repository 模式在 FastAPI 中的应用
python·fastapi
leisoo809711 小时前
涨停板封板质量打分系统实战:基于本地逐笔数据的Python实现
linux·服务器·python
c2385611 小时前
# Mini OJ — 项目详解文档
开发语言·数据库·c++
2401_8949155311 小时前
Geo 优化源码部署常见报错排查:连接失败、地图加载、地域词失效解决方案
服务器·开发语言·python·安全·php