单例模式是最常使用的一种设计模式,该模式的目的是确保在一个系统中,一个类只有一个实例
数据库链接、Socket(套接字)创建链接
其实也就是平时所说的调用第三方库,比如beautifulsoup、pymongo…
代码如下(自编写类):
class Singleton():
def __init__(self, name):
self.name = name
def do_something(self):
pass
singleton = Singleton('模块单例')
在其他脚本里,将自己写的类看作库调用
from my_singleton import singleton
在任何引用singleton的脚本里,singleton都是同一个对象,这就确保了系统中只有一个Singleton的实例。
如果对于装饰器还不太了解的话,可以自行查阅下
代码如下(示例):
def Singleton(cls):
instance = {}
def _singleton_wrapper(*args, **kargs):
if cls not in instance:
instance[cls] = cls(*args, **kargs)
return instance[cls]
return _singleton_wrapper
@Singleton
class SingletonTest(object):
def __init__(self, name):
self.name = name
slt_1 = SingletonTest('第1次创建')
print(slt_1.name)
slt_2 = SingletonTest('第2次创建')
print(slt_1.name, slt_2.name)
print(slt_1 is slt_2)
输出结果
第1次创建
第1次创建 第1次创建
True
创建slt_2 对象时,instance 字典中已经存在SingletonTest 这个key,因此直接返回了第一次创建的对象,slt_1 和 slt_2 是同一个对象。
class Singleton(object):
def __init__(self, name):
self.name = name
@classmethod
def instance(cls, *args, **kwargs):
if not hasattr(Singleton, "_instance"):
Singleton._instance = Singleton(*args, **kwargs)
return Singleton._instance
single_1 = Singleton.instance('第1次创建')
single_2 = Singleton.instance('第2次创建')
print(single_1 is single_2) # True
__new__方法是构造函数,是真正的用来创建对象的
from threading import RLock
class Singleton(object):
single_lock = RLock()#上锁
def __init__(self, name):
self.name = name
def __new__(cls, *args, **kwargs):
with Singleton.single_lock:
if not hasattr(Singleton, "_instance"):
Singleton._instance = object.__new__(cls)
return Singleton._instance
single_1 = Singleton('第1次创建')
single_2 = Singleton('第2次创建')
print(single_1.name, single_2.name) # 第2次
from threading import RLock
class SingletonType(type):
single_lock = RLock()
def __call__(cls, *args, **kwargs): # 创建cls的对象时候调用
with SingletonType.single_lock:
if not hasattr(cls, "_instance"):
cls._instance = super(SingletonType, cls).__call__(*args, **kwargs) # 创建cls的对象
return cls._instance
class Singleton(metaclass=SingletonType):
def __init__(self, name):
self.name = name
single_1 = Singleton('第1次创建')
single_2 = Singleton('第2次创建')
print(single_1.name, single_2.name) # 第1次创建 第1次创建
print(single_1 is single_2) # True
class Singleton(metaclass=SingletonType) 这行代码定义了一个类,这个类是元类SingletonType 的实例,是元类SingletonType的__new__构造出来的,Singleton是实例,那么Singleton(‘第1次创建’)就是在调用元类SingletonType 的__call__方法,__call__方法可以让类的实例像函数一样去调用
class mysql_connection:#数据库连接
__instance = None#初始定义为空
def __init__(self,ip,port,username,password):#初始化参数
self.ip = ip
self.port = port
self.username = username
self.password = password
@classmethod
def func(cls):
if cls.__instance is None:#没有则创建
cls.__instance = cls('127.0.0.1',3306,'root','root')
return cls.__instance
con1 = mysql_connection.func()
Python 单例模式 详解
python实现单例模式的5种方法