设计模式【四】:原型
伪代码
class productSetFactory{
public:
productSetFactory(ProductSet* s, ProductA* a, ProductB* b){
_protoProductSet = s;
_protoA = a;
_protoB = b;
}
ProductSet* makeSet() const{
return _protoProductSet->Clone();
}
ProductA* makeA() const{
return _protoA->Clone();
}
ProductB* makeB(){
PoductB* pB = _protoB->Clone();
pB->SetA(_protoA->Clone());
return pB;
}
}
优缺点
优点
- 运行时增删产品对象。
- 动态地获得具体的对象,通过赋值即可,而非对每种对象都要继承一个子类然后实例化。一个对象的拷贝和一个对象的初始化过程相似,但不需要一个子类继承,也就是说更简单。
- 减少继承。如果采用抽象工厂,相较于原型模式,其继承链一般更长。
缺点
原型类的每一个子类都必须实现Clone()方法。
何时使用
有时我们需要批量生产产品。这些产品只有细微差别,比如毕业证书。我们不必创建张三证书以及李四证书来继承证书类,我们只需生产证书的原型,比如张三证书,然后将名字修改为李四即可。
实现时技巧
- 原型模式在c++这种强类型,类与对象是两个概念的语言中很合适,有的语言存在“类对象”,可能更灵活而不必使用原型模式。
- 可实现一个原型管理类。所有原型在管理类内注册,尤其是当原型是动态增删时。
- 实现原型类的Clone()方法时注意不同语言对于拷贝的特性。c++,java 等需要考虑深拷贝浅拷贝的问题,尤其是c++,浅拷贝可能导致内存分配有关的错误。