Python 中的单例模式

单例模式确保一个类在整个程序中只有一个实例,并提供一个全局访问点。它通常用于管理共享资源,如数据库、日志系统或文件管理器。

这个例子向我们展示了类如何仅创建一个对象,并在每次被调用时返回同一个对象。

Python


CODEBLOCK_ddd329c8

Output

True

解释:

  • class Single: 定义了一个名为 Single 的类,instance = None:类变量用于存储单一对象。
  • def new(cls): 控制对象的创建,if cls.instance is None:检查对象是否已经存在。
  • cls.instance = super().new(cls): 只创建一次对象,而 return cls.instance:总是返回同一个对象。
  • a = Single(): 第一次调用创建了实例,b = Single():第二次调用重用了同一个实例。
  • print(a is b): 确认两个变量指向同一个对象。

实现单例模式的方法

1. 模块级单例

默认情况下,所有 Python 模块都是单例。在模块中定义的任何变量或函数在导入时都是共享的。 例如: 在下面的例子中,Singleton.py、samplemodule1.py 和 samplemodule2.py 这三个文件共享来自 Singleton.py 的一个变量。

Python


CODEBLOCK_e73232c2

Python


CODEBLOCK_9fa6a14c

Python


CODEBLOCK_715bf36e

Output

这里,samplemodule1 修改的值也反映在了 samplemodule2 中。

!singleton终端快照

解释:

  • samplemodule1 修改了 singleton.var。
  • samplemodule2 反映了更新后的值,因为模块本身就是一个单例。

2. 经典单例

经典单例仅在实例不存在时才创建一个实例。否则,它返回已创建的实例。

Python


CODEBLOCK_7c639f75

Output

True
Singleton Variable

解释:

  • if not hasattr(cls, ‘inst‘): 检查实例是否已存在。
  • cls.inst = super().new(cls): 如果不存在则创建一个新实例。
  • return cls.inst: 总是返回同一个实例。
  • s1 = Singleton()s2 = Singleton(): 两个变量都引用同一个实例。

子类示例: 让我们看看当单例类被子类化时会发生什么。

Python


CODEBLOCK_cb453f37

Output

> False

> Singleton Variable

解释:

  • SingletonChild 继承自 SingletonClass。
  • child 是 SingletonChild 的一个实例。
  • 由于 SingletonClass 是单例,child 与 singleton 共享同一个实例。
  • 访问 child.singlvariable 返回与 singleton.singlvariable 相同的值。

3. Borg 单例

Borg 单例允许不同的实例共享相同的状态。

Python


CODEBLOCK_026751ff

Output

False
Shared Variable

解释:

  • _shared: 所有实例的共享状态字典。
  • new 确保所有实例共享 _shared 状态。
  • b1c1: 不同的实例但共享相同的数据。
  • c1b1: False,实例是不同的。
  • c1.val: 从 b1 访问共享状态。

重置共享状态

Borg 单例在实例之间共享状态。重置允许在保持 Borg 结构的同时,创建一个具有独立状态的新实例。

Python


CODEBLOCK_702853d1

Output

重置共享状态会删除以前的属性。现在访问 val 会导致 AttributeError。

> Traceback (most recent call last):

> File "example.py", line 12, in

> print(nb1.val)

> AttributeError: ‘NB‘ object has no attribute ‘val‘

使用经典单例构建网络爬虫

这个例子使用经典单例模式来构建一个简单的多线程应用程序。

声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。如需转载,请注明文章出处豆丁博客和来源网址。https://shluqu.cn/49659.html
点赞
0.00 平均评分 (0% 分数) - 0