6.對象工廠基類
//MyObjectFactoryBase.h #pragma once #include "MyCreateObjectFunction.h" #include <list> #include <vector> #include <string> // //關於對象工廠,參考上面給出的文章,寫得很不錯,關於泛化對象工廠的原理闡述的很清晰. //泛化對象工廠: http://blog.csdn.net/azure1987/archive/2009/10/27/4732355.aspx // //一個 multimap, 用來存儲識別對象工廠的信息,及其可以創建的對象的版本信息 class OverRideMap; // //MyObjectFactoryBase: 工廠基類, ITK 中幾乎所有對象都是通過相應的對象工廠創建 //MyObjectFactoryBase 中包含一個靜態方法 CreateInstance(), 該方法通過已註冊的對象工廠創建對象 //第一次調用 CreateInstance(), ITK 環境變量路徑中所有的 dll 或者 靜態庫都被加載到當前進程 //爲了加載環境變量中的動態或靜態庫到當前進程, ITK 中又使用了其它庫, 我將這部分省略掉 // //1.對象工廠能夠在運行時進行版本替換 // 在程序中通過變量 m_EnabledFlag 進行控制是否可能創建特定版本的對象實例. //2.使用 multimap 存儲識別對象工廠的信息, 這樣一個對象工廠中可以有相同 key 的對象 // 我們在程序中演示瞭如何通過設置 m_EnabledFlag 創建不同版本的對象 //3.代碼中的一些方法如 GetDescription 是用來輸出對象工廠信息的 // SetEnableFlag 等是用來控制創建對象的哪一個版本 // class MyObjectFactoryBase : public MyObject { public: typedef MyObjectFactoryBase Self; typedef MyObject Superclass; typedef MySmartPointer<Self> Pointer; typedef MySmartPointer<const Self> ConstPointer; //virtual const char* GetNameOfClass() const; MyTypeMacro(MyObjectFactoryBase, MyObject); //返回一個名爲 classname 的類對象實例 //每個被加載的 MyObjectFactoryBase 都會按環境變量中的順序被詢問 //一旦有一個工廠成功創建對象並返回, 其餘工廠便不再被詢問. static MyObject::Pointer CreateInstance(const char* classname); ///////////////////////////// //註冊/註銷 對象工廠 static void RegisterFactory(MyObjectFactoryBase* ); static void UnRegisterFactory(MyObjectFactoryBase*); static void UnRegisterAllFactories(); //////////////////////////// //返回包含所有已註冊的對象工廠的鏈表 static std::list<MyObjectFactoryBase*> GetRegisteredFactories(); virtual const char* GetDescription(void) const = 0; //描述該對象工廠 //描述對象工廠及其能夠創建的對象 virtual std::list<std::string> GetClassOverrideNames(); virtual std::list<std::string> GetClassOverrideWithNames(); virtual std::list<std::string> GetClassOverrideDescriptions(); ///////////////////////////// //m_EnabledFlag:用來控制使用哪一個版本的類來創建對象, 以達到動態替換的目標 virtual std::list<bool> GetEnableFlags(); //設置/取得 指定版本類的 m_EnabledFlag 標誌. virtual void SetEnableFlag(bool flag, const char* className, const char* subclassName); virtual bool GetEnableFlag(const char* className, const char* subclassName); //Disable: 將使對象工廠不能創建該類的任何版本實例 virtual void Disable(const char* className); //OverrideInformation: 工廠及對象的版本信息, 及是否可以創建 struct OverrideInformation { std::string m_Description; //類的描述 std::string m_OverrideWithName; //重載的版本 bool m_EnabledFlag; //指示是否可以創建該版本的對象實例. MyCreateObjectFunctionBase::Pointer m_CreateObject; }; protected: MyObjectFactoryBase(); virtual ~MyObjectFactoryBase(); //註冊對象工廠, 以及其可以創建的對象版本的信息 void RegisterOverride( const char* classOverride, const char* overrideClassName, const char* description, bool enableFlag, MyCreateObjectFunctionBase* createFunction); // //對象工廠的子類實現 CreateObject 並返回創建的對象的指針,若不支持則返回 0 virtual MyObject::Pointer CreateObject(const char* classname ); private: MyObjectFactoryBase(const Self&); void operator=(const Self&); static void Initialize(); //初始化 //一個 multimap: 存儲對象工廠及其可以創建的對象的版本信息 OverRideMap* m_OverrideMap; //對象工廠列表, 包含指向已經註冊的對象工廠的指針 static std::list<MyObjectFactoryBase*>* m_RegisteredFactories; };
7.Helper 類
//MyObjectFactory.h #pragma once #include "MyObjectFactoryBase.h" //MyObjectFactory: //是一個幫助類(a helper class), 實現 Create() 方法, 用於創建一個對象實例. //對象工廠允許在運行時進行替換. //對象工廠通過運行時類型識別 RTTI 實現. template <class T> class MyObjectFactory : public MyObjectFactoryBase { public: static typename T::Pointer Create() { MyObject::Pointer ret = MyObjectFactory::CreateInstance(typeid(T).name()); //ObjectType *GetPointer () const { return m_Pointer; } //取得原始指針, 將其向下類型轉換爲 T* return dynamic_cast<T*>(ret.GetPointer()); } };
8.臨界區類實現
//MyFastMutexLock.h #pragma once //不同的平臺需要定義不同的類型,這裏只給出 windows32 例子 //不同平臺在處理時有相應的優化策略, 以保證操作的原子性. #if defined(_WIN32) #include "Windows.h" #include <winbase.h> typedef CRITICAL_SECTION FastMutexType; #endif //爲了演示, 完全可以只使用 int 即可, 但無法提供真正的加鎖功能 #ifndef _WIN32 typedef int FastMutexType; #endif //臨界區鎖類: 在修改臨界值時, 對其加鎖, 以保證修改的唯一原子性. class MyFastMutexLock { public: typedef MyFastMutexLock Self; //可以在棧上創建臨界區對象, 所以將構造函數與析構函數設爲 pubilc. MyFastMutexLock(); ~MyFastMutexLock(); //Lock, 加鎖, 使其它任何對象都不能修改被加鎖的對象 void Lock() const; //Unlock, 解鎖 void Unlock() const; protected: mutable FastMutexType m_FastMutexLock; };
9.MyObject 類的方法實現
//MyObject.h #pragma once #include "MyMacro.h" #include "MyFastMutexLock.h" #include "MySmartPointer.h" #if defined(_WIN32) //To get LONG defined #include "Windows.h" #endif //MyObject 幾乎是所有對象的基類, 實現引用計數功能, //代碼基本來 ITK 中的 LightObject 類, LightObject 在 ITK 中是最頂層的類. class MyObject { public: typedef MyObject Self; typedef MySmartPointer<Self> Pointer; //包裝爲智能指針 typedef MySmartPointer<const Self> ConstPointer; //通過對象工廠創建對象的實例 static Pointer New(); //根據已存在的對象創建一新的對象實例,允許用戶創建一個完全相同的對象 //這在需要向上類型轉換時非常有用*** virtual Pointer CreateAnother() const; //使用 New() 的對象, 應該使用 Delete() //Delete() 會調用 UnRegister 減少引用計數 //只有當該對象的引用計數減爲 0 時纔會真正刪除對象 virtual void Delete(); //運行時類型識別, 返回某對象的具體類名. virtual const char *GetNameOfClass() const {return "MyObject";} //Used to avoid dll boundary problems. void* operator new(size_t); void* operator new[](size_t); void operator delete(void*); void operator delete[](void*, size_t); //增加與減少引用計數 virtual void Register() const; virtual void UnRegister() const; //返回該類對象實例的引用計數 virtual int GetReferenceCount() const { return static_cast<int>(m_ReferenceCount); } //設置該類對象的引用計數值. virtual void SetReferenceCount(int); protected: MyObject() : m_ReferenceCount(1) { } virtual ~MyObject(); //不同的平臺, 需要定義不同的類型, 這裏只簡單使用 int 型. 引用計數. #if (defined(WIN32) || defined(_WIN32)) typedef LONG InternalReferenceCountType; #else typedef int InternalReferenceCountType; #endif //引用計數 mutable InternalReferenceCountType m_ReferenceCount; //mutable int m_ReferenceCount; //臨界區鎖, 用於對臨界區變量加鎖 mutable MyFastMutexLock m_ReferenceCountLock; private: MyObject(const Self&); void operator=(const Self&); };
10.對象工廠基類實現
#if defined(_MSC_VER) #pragma warning ( disable : 4786 ) #endif #include "MyObjectFactoryBase.h" #include <stdlib.h> #include <ctype.h> #include <string.h> #include <algorithm> #include <map> ////////////////////////////////////////////////////// //該類用於清除所有已經註冊的對象工廠. class CleanUpObjectFactory { public: inline void Use(){ } ~CleanUpObjectFactory() { MyObjectFactoryBase::UnRegisterAllFactories(); } }; //定義一全局靜態變量, 在程序生命週期結束時析構, 用於註銷所有對象工廠 static CleanUpObjectFactory CleanUpObjectFactoryGlobal; //////////////////////////////////////// //StringOverMap, 使用 typedef 進行類型定義, 避免出現名字過長的警告. typedef std::multimap<std::string, MyObjectFactoryBase::OverrideInformation> StringOverMapType; //用於存儲 <classID, facotoryInfo> //classID 對象工廠的標識 //factoryInfo 該對象工廠的信息, 包含其可以創建的對象的所有版本信息 class OverRideMap : public StringOverMapType { }; ///////////////////////////////////////////////////// //靜態變量初始化, 已註冊的對象工廠鏈表. std::list<MyObjectFactoryBase*>* MyObjectFactoryBase::m_RegisteredFactories = 0; //構造函數 MyObjectFactoryBase::MyObjectFactoryBase() { m_OverrideMap = new OverRideMap; } //析構, 卸載已加載的對象工廠. MyObjectFactoryBase::~MyObjectFactoryBase() { m_OverrideMap->erase(m_OverrideMap->begin(), m_OverrideMap->end()); delete m_OverrideMap; } //使用已註冊的對象工廠創建類名爲 classname 的對象實例. MyObject::Pointer MyObjectFactoryBase::CreateInstance(const char* classname) { if( !MyObjectFactoryBase::m_RegisteredFactories ) { MyObjectFactoryBase::Initialize(); } for( std::list<MyObjectFactoryBase*>::iterator i = m_RegisteredFactories->begin(); i != m_RegisteredFactories->end(); ++i ) { //遍歷已註冊的對象列表, 如果某個對象工廠成功創建對象, 則返回 MyObject::Pointer newobject = (*i)->CreateObject(classname); if(newobject) { newobject->Register(); return newobject; } } return 0; } //初始化 void MyObjectFactoryBase::Initialize() { //全局靜態變量, 用於最後註銷所有的對象工廠 CleanUpObjectFactoryGlobal.Use(); //已經初始化過了, 返回 if( MyObjectFactoryBase::m_RegisteredFactories ) { return; } MyObjectFactoryBase::m_RegisteredFactories = new std::list<MyObjectFactoryBase*>; } //註冊對象工廠, 添加至鏈表中. void MyObjectFactoryBase::RegisterFactory(MyObjectFactoryBase* factory) { //先進行初始化,然後將該對象工廠加入到對象工廠鏈表中 MyObjectFactoryBase::Initialize(); MyObjectFactoryBase::m_RegisteredFactories->push_back(factory); factory->Register(); } //清除已經清冊的名爲 factory 的對象工廠 void MyObjectFactoryBase::UnRegisterFactory(MyObjectFactoryBase* factory) { if( !MyObjectFactoryBase::m_RegisteredFactories ) return; for ( std::list<MyObjectFactoryBase*>::iterator i = m_RegisteredFactories->begin(); i != m_RegisteredFactories->end(); ++i ) { if ( factory == *i ) { factory->UnRegister(); m_RegisteredFactories->remove(factory); return; } } } //清除所有已註冊的對象工廠, 並刪除對象工廠列表 void MyObjectFactoryBase::UnRegisterAllFactories() { if ( MyObjectFactoryBase::m_RegisteredFactories ) { for ( std::list<MyObjectFactoryBase*>::iterator f = m_RegisteredFactories->begin(); f != m_RegisteredFactories->end(); ++f ) { (*f)->UnRegister(); } //刪除對象工廠鏈表... delete MyObjectFactoryBase::m_RegisteredFactories; MyObjectFactoryBase::m_RegisteredFactories = 0; } } //返回包含所有已註冊的對象工廠的鏈表... std::list<MyObjectFactoryBase*> MyObjectFactoryBase::GetRegisteredFactories() { return *MyObjectFactoryBase::m_RegisteredFactories; } /////////////////////////////// //描述對象工廠及其能夠創建的對象 std::list<std::string> MyObjectFactoryBase::GetClassOverrideNames() { std::list<std::string> ret; for ( OverRideMap::iterator i = m_OverrideMap->begin(); i != m_OverrideMap->end(); ++i ) { ret.push_back((*i).first); } return ret; } std::list<std::string> MyObjectFactoryBase::GetClassOverrideWithNames() { std::list<std::string> ret; for ( OverRideMap::iterator i = m_OverrideMap->begin(); i != m_OverrideMap->end(); ++i ) { ret.push_back((*i).second.m_OverrideWithName); } return ret; } std::list<std::string> MyObjectFactoryBase::GetClassOverrideDescriptions() { std::list<std::string> ret; for ( OverRideMap::iterator i = m_OverrideMap->begin(); i != m_OverrideMap->end(); ++i ) { ret.push_back((*i).second.m_Description); } return ret; } //註冊對象工廠, 以及其可以創建的對象的版本信息 void MyObjectFactoryBase::RegisterOverride( const char* classOverride, const char* subclass, const char* description, bool enableFlag, MyCreateObjectFunctionBase* createFunction) { MyObjectFactoryBase::OverrideInformation info; info.m_Description = description; info.m_OverrideWithName = subclass; //具體的子類 info.m_EnabledFlag = enableFlag; //是否使用該子類版本 info.m_CreateObject = createFunction; m_OverrideMap->insert(OverRideMap::value_type(classOverride, info)); } // MyObject::Pointer MyObjectFactoryBase::CreateObject(const char* classname) { OverRideMap::iterator start = m_OverrideMap->lower_bound(classname); OverRideMap::iterator end = m_OverrideMap->upper_bound(classname); int m = 0; for ( OverRideMap::iterator i = start; i != end; ++i ) { //(*i).second.m_EnabledFlag = true; 則使用該工廠創建該版本的對象實例 if ( i != m_OverrideMap->end() && (*i).second.m_EnabledFlag) { //調用了 MyCreateObjectFunction::CreateObject(); //MyCreateObjectFunction 是用於創建對象的回調函數 return (*i).second.m_CreateObject->CreateObject(); } } return 0; } /////////////////////////// //m_EnabledFlag: 控制對象工廠可以創建的對象版本 void MyObjectFactoryBase::SetEnableFlag(bool flag, const char* className,const char* subclassName) { OverRideMap::iterator start = m_OverrideMap->lower_bound(className); OverRideMap::iterator end = m_OverrideMap->upper_bound(className); for ( OverRideMap::iterator i = start; i != end; ++i ) { if ( (*i).second.m_OverrideWithName == subclassName ) { (*i).second.m_EnabledFlag = flag; } } } bool MyObjectFactoryBase ::GetEnableFlag(const char* className, const char* subclassName) { OverRideMap::iterator start = m_OverrideMap->lower_bound(className); OverRideMap::iterator end = m_OverrideMap->upper_bound(className); for ( OverRideMap::iterator i = start; i != end; ++i ) { if ( (*i).second.m_OverrideWithName == subclassName ) { return (*i).second.m_EnabledFlag; } } return 0; } void MyObjectFactoryBase::Disable(const char* className) { OverRideMap::iterator start = m_OverrideMap->lower_bound(className); OverRideMap::iterator end = m_OverrideMap->upper_bound(className); for ( OverRideMap::iterator i = start; i != end; ++i ) { (*i).second.m_EnabledFlag = 0; } } std::list<bool> MyObjectFactoryBase::GetEnableFlags() { std::list<bool> ret; for( OverRideMap::iterator i = m_OverrideMap->begin(); i != m_OverrideMap->end(); ++i) { ret.push_back((*i).second.m_EnabledFlag); } return ret; }