[ 永远的UNIX::UNIX技术资料的宝库 ]

首页 > 应用专题 > 其它 > 正文
 

MFC中Dynamic Creation技术的实现原理

来源:不详 (2006-06-29 14:14:22)

Dynamic Creation-动态创建

(本文以“MFCRTTI技术的实现原理”为基础进行说明)

 

1、需求

给定一个类的名字CName,能够动态地创建该类的对象

 

2、需求分析

2.1、提供创建CName实例的函数,将该函数的指针作为CName的类型信息进行存储;

2.2、创建CName实例的函数的指针能够在CName实例化前被使用;

2.3、使用创建CName实例的函数的指针创建CName的实例;

2.4、使用方法

l         动态创建CName的实例

CRuntimeClass* pRuntimeClass = RUNTIME_CLASS(CName)

CObject* pObject = pRuntimeClass->CreateObject();//CName必须有一个缺省构造函数

Assert( pObject->IsKindOf(RUNTIME_CLASS(CName));//IsKindOf检测是否是CName类的实例

 

4、普通实现

4.1CRuntimeClass

struct CRuntimeClass

{

LPCSTR m_lpszClassName; //类的名字

CRuntimeClass* m_pBaseClass; //父类类型信息

CObject* (PASCAL* m_pfnCreateObject)(); // 创建对象的函数的指针

BOOL IsDerivedFrom(const CRuntimeClass* pBaseClass) const

{   

const CRuntimeClass* pClassThis = this;

while (pClassThis != NULL)   //循环取父类的类型信息

{

if (pClassThis == pBaseClass) return TRUE;

pClassThis = pClassThis->m_pBaseClass;

}

return FALSE;

}

CObject* CreateObject() //利用函数指针m_pfnCreateObject创建对象

{   

if (m_pfnCreateObject == NULL) { return NULL;}

CObject* pObject =  (*m_pfnCreateObject)(); 

return pObject;

};

4.2CName

class CName:: CObject

{

public:

//必须有缺省构造函数

CName();

//取得静态变量classCName的指针

virtual CRuntimeClass* GetRuntimeClass() const

{

return (CRuntimeClass*) (&CName::classCName);

};

static CObject* PASCALCreateObject()  

{

return new CName;

}

public:

//静态变量,保存类型信息,父类类型对象指定为继承的类的静态类型对象

      static const CRuntimeClass classCName =

 { "CName ", (CRuntimeClass*) (&CObject:: classCObject) , CName:: CreateObject };

};

 

5、通过宏来简化实现

5.1、宏的定义

l         DECLARE_DYNAMIC

#define DECLARE_DYNAMIC(class_name) \

public:  static const AFX_DATA CRuntimeClass class##class_name; \

                     virtual CRuntimeClass* GetRuntimeClass() const; \

l         IMPLEMENT_DYNAMIC

#define IMPLEMENT_DYNAMIC(class_name, base_class_name) \

             IMPLEMENT_RUNTIMECLASS(class_name, base_class_name, NULL)

l         IMPLEMENT_RUNTIMECLASS

#define IMPLEMENT_RUNTIMECLASS(class_name, base_class_name, pfnNew) \

             AFX_COMDAT const AFX_DATADEF CRuntimeClass class_name::class##class_name = { \

                    #class_name, RUNTIME_CLASS(base_class_name), pfnNew, }; \

             CRuntimeClass* class_name::GetRuntimeClass() const  { return RUNTIME_CLASS(class_name); } \

l         DECLARE_DYNCREATE

#define DECLARE_DYNCREATE(class_name) \

DECLARE_DYNAMIC(class_name) \

static CObject* PASCAL CreateObject();

l         IMPLEMENT_DYNCREATE

#define IMPLEMENT_DYNCREATE(class_name, base_class_name) \

CObject* PASCAL class_name::CreateObject()   { return new class_name; } \ //必须有缺省构造函数

             IMPLEMENT_RUNTIMECLASS(class_name, base_class_name, class_name::CreateObject)

5.2、简化后的实现

l         CName

//头文件

class CName:: CObject

{

DECLARE_DYNCREATE (CName)

};

//源文件

IMPLEMENT_ DYNCREATE (CName, CObject)

 

6、总结

6.1、静态变量的使用;

6.2、宏的使用;

6.3、为弄清原理,对MFC的源代码进行了简化;


(http://www.fanqiang.com)



 
 相关文章

 

★  感谢所有的作者为我们学习技术知识提供了一条捷径  ★
www.fanqiang.com