该形式的工厂模式是我项目中用到的方法,属于很成熟的模版,读者可以直接拿来在自己项目中使用。个人感觉这种方法真正做到了“开放封闭”的原则,最大好处是用户产品类的设计完全不依赖于该模式的实现,比如提供必须的相关函数等。如果不理解工厂模式的话,请参考网上其它文章,本实现在理解上有一点小小的难度。好东西,大家慢慢享用,话不多说,先放代码!
首先是产品基类,它相当于一个接口,产品需要有什么动作就写在这里吧!
#ifndef _CPRODUCTBASE_H_
#define _CPRODUCTBASE_H_
enum PRODUCT_TYPE{PT_NOKIA=0, PT_APPLE, PT_GOOGLE};
class CProductBase{
public:
CProductBase(){}
~CProductBase(){}
public:
virtual void doSomething()=0;
};
#endif
其次,工厂类。这个类不是很好理解,首先要明白CreateByType是根据产品类型先创建了一个工厂单元,由工厂单元创建产品,map中保存的也是工厂单元。
#ifndef _DYNAMICFACTORY_H_
#define _DYNAMICFACTORY_H_
#include <map>
#include "CProductBase.h"
using namespace std;
class CDynamicFactory{
protected:
CDynamicFactory(){ m_mapType2Factor.clear(); }
public:
class CFactoryUnitBase{
public:
virtual CProductBase* BuildProduct()=0;
};
typedef std::map<PRODUCT_TYPE, CFactoryUnitBase*> MAP_TYPE_UNIT;
typedef std::map<PRODUCT_TYPE, CFactoryUnitBase*>::iterator MAP_TYPE_UNIT_ITERATOR;
static CDynamicFactory& GetInstance()
{
static CDynamicFactory nodeFactory;
return nodeFactory;
}
CProductBase* CreateByType(PRODUCT_TYPE emType)
{
CFactoryUnitBase* pFactoryUnit(NULL);
CProductBase* pProduct(NULL);
MAP_TYPE_UNIT_ITERATOR it = m_mapType2Factor.find(emType);
if (it != m_mapType2Factor.end())
{
pFactoryUnit= it->second;
pProduct = pFactoryUnit->BuildProduct();
}
return pProduct;
}
void RegisterFactory(PRODUCT_TYPE emType, CFactoryUnitBase* pFactoryUnit)
{
m_mapType2Factor[emType] = pFactoryUnit;
}
private:
MAP_TYPE_UNIT m_mapType2Factor;
};
#endif下面是动态创建的宏定义了,为什么能在程序运行之前map中已经有了相应类型产品的工厂,和static class_name::FactoryUnit __factory(class_name::ProductType);有很大关系,它定义了一个全局静态变量,名字可以随便取,由于初始化是在编译时进行(是吧,不是太确定?),所以就调用了FactoryUnit构造函数,然后就执行了里面的RegisterFactory。
#ifndef _PRODUCTCREATOR_H_
#define _PRODUCTCREATOR_H_
#include "DynamicFactory.h"
#define DECLARE_DYNAMIC() public: static const PRODUCT_TYPE ProductType; class FactoryUnit : public CDynamicFactory::CFactoryUnitBase { public: FactoryUnit(PRODUCT_TYPE emType) { CDynamicFactory::GetInstance().RegisterFactory(emType,this); } virtual CProductBase* BuildProduct(); };
#define IMPLEMENT_DYNAMIC(class_name, emType) const PRODUCT_TYPE class_name::ProductType = emType; static class_name::FactoryUnit __factory(class_name::ProductType); CProductBase* class_name::FactoryUnit::BuildProduct() { class_name* pProduct = new class_name; return pProduct; }
#endif#ifndef _CGOOGLE_H_
#define _CGOOGLE_H_
#include "DynamicFactory.h"
#include "ProductCreator.h"
#include "CProductBase.h"
class CGoogle : public CProductBase{
DECLARE_DYNAMIC()
public:
virtual void doSomething();
};
#endif
#include "CGoogle.h"
#include <iostream>
using std::cout;
using std::endl;
IMPLEMENT_DYNAMIC(CGoogle, PT_GOOGLE);
void CGoogle::doSomething(){
cout<<"In Google"<<endl;
}#ifndef _CNOKIA_H_
#define _CNOKIA_H_
#include "DynamicFactory.h"
#include "ProductCreator.h"
#include "CProductBase.h"
class CNokia: public CProductBase{
DECLARE_DYNAMIC()
public:
virtual void doSomething();
};
#endif#include "CNokia.h"
#include <iostream>
using std::cout;
using std::endl;
IMPLEMENT_DYNAMIC(CNokia, PT_NOKIA);
void CNokia::doSomething(){
cout<<"In Nokia"<<endl;
}main函数。
#include "DynamicFactory.h"
#include "ProductCreator.h"
#include "CGoogle.h"
#include "CNokia.h"
int main()
{
CNokia *p = (CNokia*)CDynamicFactory::GetInstance().CreateByType(PT_NOKIA);
p->doSomething();
delete p; //注意
p = NULL;
return 0;
}
下面是另一网友用动态创建的方法写的工厂模式,读者可以一起参考:
http://blog.csdn.net/happyanger6/article/details/7277638
设计模式之工厂模式:模拟DECLARE_DYNAMIC和IMPLEMENT_DYNAMIC动态创建类对象,布布扣,bubuko.com
设计模式之工厂模式:模拟DECLARE_DYNAMIC和IMPLEMENT_DYNAMIC动态创建类对象
原文地址:http://blog.csdn.net/zhangjun03402/article/details/28898703