Python中如何像iOS开发一样将Model封装成单例使用?
null
Python中如何像iOS开发一样将Model封装成单例使用?
5 回复
单机就是个伪全局,可以使用 classmethed
在Python里搞单例模式,方法挺多的。iOS开发里那种shared静态实例的方式,在Python里也能实现,而且更简单。
最Pythonic的方式是用模块导入的特性。Python模块在导入时只会执行一次,天然就是单例。比如你有个UserModel类,可以这么写:
# model.py
class UserModel:
def __init__(self):
self.data = {}
print("UserModel实例化") # 只会打印一次
def update_data(self, key, value):
self.data[key] = value
def get_data(self):
return self.data.copy()
# 创建全局实例
shared = UserModel()
然后在其他地方导入这个shared实例:
from model import shared
# 第一次使用
shared.update_data('name', '张三')
print(shared.get_data()) # {'name': '张三'}
# 在其他模块中导入的也是同一个实例
from model import shared
print(shared.get_data()) # 还是{'name': '张三'}
如果你想要更像iOS的语法,可以用类属性加__new__方法:
class ConfigModel:
_instance = None
def __new__(cls):
if cls._instance is None:
cls._instance = super().__new__(cls)
cls._instance.settings = {}
return cls._instance
@classmethod
def shared(cls):
return cls()
# 使用方式
config1 = ConfigModel.shared()
config1.settings['theme'] = 'dark'
config2 = ConfigModel.shared()
print(config2.settings) # {'theme': 'dark'}
print(config1 is config2) # True,是同一个实例
还有个更简单的方法是用装饰器:
def singleton(cls):
instances = {}
def get_instance(*args, **kwargs):
if cls not in instances:
instances[cls] = cls(*args, **kwargs)
return instances[cls]
return get_instance
@singleton
class AppState:
def __init__(self):
self.state = {}
# 使用
state1 = AppState()
state2 = AppState()
print(state1 is state2) # True
模块导入的方式最简单实用,推荐用这个。
这个对于 Python 有省事简单方法,在 python 中把要单例的东西放到一个文件(模块)中,然后所有调用者都直接 import 就是天然单例了。
闲得没事可以用__new__方法,创建好类的全局实例。在实例化时都返回那个全局实例就可以了。
这个样子哇。那懂了。
get
import 是天然的单列

