pengkunstone 2020-02-22
单例模式就是确保一个类只有一个实例.当你希望整个系统中,某个类只有一个实例时,单例模式就派上了用场.比如,某个服务器的配置信息存在在一个文件中,客户端通过AppConfig类来读取配置文件的信息.如果程序的运行的过程中,很多地方都会用到配置文件信息,则就需要创建很多的AppConfig实例,这样就导致内存中有很多AppConfig对象的实例,造成资源的浪费.其实这个时候AppConfig我们希望它只有一份,就可以使用单例模式.
单例模式是一种软件设计模型。在面向对象编程中,通过单例模型只能创建一个类实例,也就是一个类永远只有一个实例对象。在工作中,为了确保某一个类只会创建一个实例,就需要使用单例模型。实现单例的方法有:
def singleton_func(cls): instances = {} def _singleton(*args, **kwargs): if cls not in instances: instances[cls] = cls(*args, **kwargs) return instances[cls] return _singleton @singleton_func class Phone(object): def Phone_id(self): return id(self) p1 = Phone() p2 = Phone() print(p1.phone_id()) print(p2.phone_id())
class SingletonInstance(object): def __call__(self, *args, **kwargs): return self SingletonInstance = SingletonInstance() s1 = SingletonInstance() s2 = SingletonInstance() print(id(s1)) print(id(s2))
class SingletonDecorator(object): _instance = None def __init__(self, cls): self._cls = cls def __call__(self, *args, **kwargs): if self._instance is None: self._instance = self._cls(*args, **kwargs) return self._instance @SingletonDecorator class Phone(object): def phone_id(self): return id(self) p1 = Phone() p2 = Phone() print(p1.phone_id()) print(p2.phone_id())
class SingletonClass(object): _instance = None def __new__(cls, *args, **kwargs): if cla._instance is None: cls._instance = super(SingletonClass, self).__new__(cls) return cls._instance _is_init = False def __init__(self): if self._is_init is False: print(‘-*-‘) self._is_init = True s1 = SingletonClass() s2 = SingletonClass() print(id(s1)) print(id(s2))
②实现单例模式的方法有多种,之前再说元类的时候用call方法实现了一个单例模式,另外Python的模块就是一个天然的单例模式;
# 使用new关键字来实现一个单例模式 class Book: def __new__(cls, title): if nothasattr(cls, "_ins") cls._ins=super().__new__() print(‘in__new__‘) return cls._ins def __init__(self, title): print(‘in__init__‘) super().__init__() self.title = title if __name__ == ‘__main__‘: b = Book(‘The Spider Book‘) b2 = Book(‘The Flask Book‘) print(id(b)) print(id(b2)) print(b.title) print(b2.title)
class SingletonMeta(type, object): def __init__(self, *args, **kwargs): self._instance = None super(SingletonMeta, self).__init__(*arg, **kwargs) # _instance = None def __call__(self, *args, **kwargs): if self._instance is None self._instance = super(SingletonMeta, self).__call__(*args, **kwargs) return self._instance class Phone(object, metaclass = SingletonMeta): def phone_id(self): return id(self) p1 = Phone() p2 = Phone() print(p1.phone_id()) print(p2.phone_id())
②元类(metaclass)实现单例
class Singleton(type): def __init__(self, *args, **kwargs): print("in __init__") self.__instance = None super(Singleton, self).__init__(*args, **kwargs) def __call__(self, *args, **kwargs): print("in __call__") if self.__instance is None: self.__instance = super(Singleton, self).__call__(*args, **kwargs) return self.__instance class Foo(metaclass=Singleton): pass foo1 = Foo() foo2 = Foo() print(foo1 is foo2)
class Singleton: def __new__: # 关键在于这,每一次实例化的时候,我们都只会返回这同一个instance对象 if not hasattr: cls.instance =