Title

三种单例模式

  python面试中一般会问到单例模式,下面介绍一下常见的3种python单例模式

第一种 __new__方法
class Foo(object):
    def __init__(self,name):
        self.name = name
    def __new__(cls, *args, **kwargs):
        if not hasattr(cls,'_instance'):
            cls._instance = object.__new__(cls)
        return cls._instance
    # def __new__(cls, *args, **kwargs):
    #     if not hasattr(cls, '_instance'):
    #         cls._instance = super(Foo, cls).__new__(cls)
    #     return cls._instance
f1= Foo('alex')
print(f1.name,f1) # alex <__main__.Foo object at 0x0000000002249630>

f2= Foo('egon')
print(f2.name,f2) # egon <__main__.Foo object at 0x0000000002249630>

print(f1 is f2)   # True

# 反例
class Foo(object):
    def __init__(self,name):
        self.name = name
f3= Foo('alex')
print(f3.name,f3) # alex <__main__.Foo object at 0x000000000215B4E0>

f4= Foo('egon')
print(f4.name,f4) # egon <__main__.Foo object at 0x0000000002AAF0B8>

print(f3 is f4)   # False
  第二种 自定义classmethod方法
class Foo:
    _instance = None

    def __init__(self, name):
        self.name = name

    @classmethod
    def get_instance(cls, name):      # 类方法, 第一个参数默认是类这个对象
        if cls._instance:             # 判断如果这个静态字段为真(已经存在实例)
            cls._instance.name=name   # 重新给name赋值
            return cls._instance      # 直接返回这个实例
        else:                         # 如果实例不存在
            obj = cls(name)           # 在类的内部创建一个实例,内部调用了init构造方法
            cls._instance = obj       # 将该实例赋值给类的静态字段,防止下次重复创建
            return obj                # 将新创建的对象返回


# 经过上面的修改, 如果想实现单例模式, 就不能再使用init构造方法来创建对象了
# f1= Foo('alex')
# print(f1.name,f1) # alex <__main__.Foo object at 0x0000000002289A90>
#
# f2= Foo('egon')
# print(f2.name,f2) # egon <__main__.Foo object at 0x00000000027B95C0>
#
# print(f1 is f2)   # False

# 而是通过类方法创建
f3 = Foo.get_instance("alex")  # 第一次会创建对象
print(f3.name,f3)              # alex <__main__.Foo object at 0x0000000002A9F0B8>

f4 = Foo.get_instance("egon")  # 第二次会使用第一次创建的对象
print(f4.name,f4)              # egon <__main__.Foo object at 0x0000000002A9F0B8>

print(f3 is f4)                # True
  第三种 import方法
# mysingleton.py
class My_Singleton(object):
    def foo(self):
        pass
 
my_singleton = My_Singleton()
 
# to use
from mysingleton import my_singleton
 
my_singleton.foo()

  

原文地址:https://www.cnblogs.com/guotianbao/p/7902527.html