Python单例模式五大实现方法

单例模式确保类只有一个实例并提供全局访问,适用于全局配置、数据库连接和日志共享等场景。实现方式包括模块、装饰器、类、new方法和元类。其优点在于节省内存和避免资源重复,但可能导致可扩展性和测试性降低。
摘要由CSDN通过智能技术生成

单例模式:确保类有且只有一个特定类型的对象,并提供全局访问点。

作用:程序运行过程中其实只有一个实例在运行;避免资源消耗及保证数据安全与全局性等。

场景:全局服务器配置;数据库连接;日志文件共享…

实现方式:

一. 模块
01.把函数与数据写入模块,实现单例对象
# singleton_by_module.py
class Singleton(object):
    def foo(self):
        pass


singleton = Singleton()
02.使用时直接导入/单例模式对象=singleton_by_module.py
# test.py
from singleton_by_module import Singleton

t = Singleton()
二. 装饰器
# singleton_by_decorator.py
def Singleton(cls):
    _instance = {}

    def _singleton(*args, **kwargs):
        if cls not in _instance:
            print('get ready init')
            _instance[cls] = cls(*args, **kwargs)
            print('get ready success')
        else:
            print('already init')
        return _instance[cls]

    return _singleton


@Singleton
class A(object):
    def __init__(self, a=0):
        self.a = a


a1 = A(1)
a2 = A(2)
print("a1_id:{},a1.a:{}".format(id(a1), a1.a))
print("a2_id:{},a2.a:{}".format(id(a1), a1.a))
01.程序运行:创建类对象a1调用,正常打印;当a1创建并调用由于实例已存在,调用a1,所以说他们的内存id一样。
三. 类
01.使用线程锁解决线程问题
import time
import threading
class Singleton:
    _instance_lock = threading.Lock()

    def __init__(self):
        time.sleep(1)

    @classmethod
    def instance(cls, *args, **kwargs):
        if not hasattr(Singleton, "_instance"):
            with Singleton._instance_lock:
                if not hasattr(Singleton, "_instance"):
                    Singleton._instance = Singleton(*args, **kwargs)
        return Singleton._instance

def task(arg):
    obj = Singleton.instance()
    print(obj)
for i in range(10):
    t = threading.Thread(target=task,args=[i,])
    t.start()
time.sleep(20)
obj = Singleton.instance()
print(obj)
四.new方法
01.类实例前先执行new方法 ;然后执行init方法。
import threading
class Singleton:
    _instance_lock = threading.Lock()

    def __init__(self):
        pass

    def __new__(cls, *args, **kwargs):
        if not hasattr(Singleton, "_instance"):
            with Singleton._instance_lock:
                if not hasattr(Singleton, "_instance"):
                    Singleton._instance = super(Singleton,cls).__new__(cls,*args, **kwargs)
        return Singleton._instance

obj1 = Singleton()
obj2 = Singleton()
print(obj1,obj2)

def task(arg):
    obj = Singleton()
    print(obj)

for i in range(5):
    t = threading.Thread(target=task,args=[i,])
    t.start()
五.metaclass元类
01.类由type创建,创建类时,type的init方法自动执行,类() 执行type的call方法(类的new方法,类的init方法) 
02.对象由类创建,创建对象时,类的init方法自动执行,对象()执行类的call方法 
import threading

class SingletonType(type):
    _instance_lock = threading.Lock()
    def __call__(cls, *args, **kwargs):
        if not hasattr(cls, "_instance"):
            with SingletonType._instance_lock:
                if not hasattr(cls, "_instance"):
                    cls._instance = super(SingletonType,cls).__call__(*args, **kwargs)
        return cls._instance

class Foo(metaclass=SingletonType):
    def __init__(self,name):
        self.name = name

obj1 = Foo('name')
obj2 = Foo('name')
print(obj1,obj2)
单例模式优缺点:

优点:全局只有一个实例,节省内存空间;避免开销;避免多重复用。
缺点:可扩展性差;违背单一原则;不利于测试。

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值