def
用原型实例指定创建对象的种类, 并且通过拷贝这些原型创建新的对象。
usage
● 性能优良
原型模式是在内存二进制流的拷贝, 要比直接new一个对象性能好很多, 特别是要在一个循环体内产生大量的对象时, 原型模式可以更好地体现其优点。
● 逃避构造函数的约束
这既是它的优点也是缺点, 直接在内存中拷贝, 构造函数是不会执行的 。 优点就是减少了约束, 缺点也是减少了约束, 需要大家在实际应用时考虑。
● 资源优化场景
类初始化需要消化非常多的资源, 这个资源包括数据、 硬件资源等。
● 性能和安全要求的场景
通过new产生一个对象需要非常繁琐的数据准备或访问权限, 则可以使用原型模式。
● 一个对象多个修改者的场景
一个对象需要提供给其他对象访问, 而且各个调用者可能都需要修改其值时, 可以考虑使用原型模式拷贝多个对象供调用者使用。
code
class Prototype(object):
value = 'default'
def clone(self, **attrs):
"""Clone a prototype and update inner attributes dictionary"""
# Python in Practice, Mark Summerfield
obj = self.__class__()
obj.__dict__.update(attrs)
return obj
class PrototypeDispatcher(object):
def __init__(self):
self._objects = {}
def get_objects(self):
"""Get all objects"""
return self._objects
def register_object(self, name, obj):
"""Register an object"""
self._objects[name] = obj
def unregister_object(self, name):
"""Unregister an object"""
del self._objects[name]
def main():
dispatcher = PrototypeDispatcher()
prototype = Prototype()
d = prototype.clone()
a = prototype.clone(value='a-value', category='a')
b = prototype.clone(value='b-value', is_checked=True)
dispatcher.register_object('objecta', a)
dispatcher.register_object('objectb', b)
dispatcher.register_object('default', d)
print([{n: p.value} for n, p in dispatcher.get_objects().items()])
if __name__ == '__main__':
main()
### OUTPUT ###
# [{'objectb': 'b-value'}, {'default': 'default'}, {'objecta': 'a-value'}]