Python 常见的单例模式

单例模式(Singleton)也叫单态模式,是设计模式中最为简单的一种模式,甚至有些模式大师都不称其为模式,称其为一种实现技巧,因为设计模式讲究对象之间的关系的抽象,而单例模式只有自己一个对象,也因此有些设计大师把其称为设计模式之一

单例模式保证了在程序的不同位置都可以且仅可以取到同一个对象的实例,如果实例不存在,会创建一个实例;否则返回这个实例。单例是一个类,可以为其提供相应的操作方法,便于管理,节约内存资源。

应用场景:

windows的任务管理器,只能打开一个;

网站的计数器,一般采用单例模式实现,否则难以同步;

多线程的线程池,便于对线程的控制;

应用程序的日志应用,一般是用单例模式,是由于共享的日志文件一直处于打开状态,只能有一个实例去操作;

。。。。。。

 

单例模式实现方法:

 

装饰器实现单例模式:

def singleton(cls):
    _instance = {}

    def inner(*args,**kwargs):
        if cls not in _instance:
            _instance[cls] = cls(*args,**kwargs)
        return _instance[cls]
    return inner
    
@singleton
class Examples(object):
    def __init__(self,*args,**kwargs):
        pass

examples1 = Examples()
examples2 = Examples()
print(id(examples1) == id(examples2))
#结果:
#True

@singleton
class Examples1(object):
    def __init__(self,*args,**kwargs):
        pass

examples3 = Examples1()
print(id(examples1) == id(examples3))
#结果:
#False

 通过打印结果可知,第一次打印结果是True,说明它们指向了同一个对象,第二次打印结果是False;

当第一次调用这个类时,会将类地址作为键保存在_instance中,值为实例;每次创造实例时,会先看该类是否存在,存在直接返回即可,否则新建一个实例并存放到_instance中,将实例返回;

 

__new__实现单例模式:

class Singleton(object):

    __instance = None
    def __new__(cls,*args,**kwargs):
        if not cls.__instance:
            cls.__instance = object.__new__(cls)
        return cls.__instance

single1 = Singleton()
single2 = Singleton()
print(id(single1) == id(single2))
#结果:
#True

_instance存放实例,有责返回实例,无则创建实例保存并返回

 

模块方式单例模式

python的模块是天然的单例模式,因为模块在第一次导入时,会生成 .pyc 文件,当第二次导入时,就会直接加载 .pyc 文件,而不会再次执行模块代码。

因此,我们只需把相关的函数和数据定义在一个模块中,就可以获得一个单例对象了。如果我们真的想要一个单例类,可以考虑这样做:

 

#sinton.py
class Singleton1(object):
    def foo(self):
        pass
mysinton = Singleton1()

在其他文件中运用方法:

from sinton import mysinton

mysinton.foo()

 

基于metaclass实现单例模式

先了解下type创造类的方法

def func(self):
    print("do sth")

Singleton = type("Singleton", (), {"func": func})

c = Singleton()
c.func()

以上就是使用type创造的一个类,这是metaclass实现单例模式的基础

单例模式如下

class Singleton(type):
    _instances = {}
    def __call__(cls, *args, **kwargs):
        if cls not in cls._instances:
            cls._instances[cls] = super(Singleton, cls).__call__(*args, **kwargs)
        return cls._instances[cls]

class Cls4(metaclass=Singleton):
    pass

cls1 = Cls4()
cls2 = Cls4()
print(id(cls1 ) == id(cls2))
#结果:
#True

这里,我们将 metaclass 指向 Singleton 类,让 Singleton 中的 type 来创造新的 Cls4 实例

以上就是几种方式实现的单例模式,还有一些其他的实现方式,可以自行百度了解下;

 

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值