为什么是 DECLARE_DYNAMIC &DYNAMIC_DOWNCAST 是否需要 IMPLEMENT_DYNAMIC?
我有两个班级:
/*Switch.h*/
class CSwitch : public CDeviceEntity {}
/*EndSystem.h*/
class CEndSystem : public CDeviceEntity {}
但是当我使用时:
CDeviceEntity* dev = NULL;
dev = topo->headList[i]->node;
if ( DYNAMIC_DOWNCAST( CEndSystem, dev ) != NULL ) {}
"DYNAMIC_DOWNCAST
" 总是返回 not NULL
而 dev 是一种 class CEndSystem
或 class CSwitch
.
"DYNAMIC_DOWNCAST
" always returns not NULL
while dev is kind of class CEndSystem
or class CSwitch
.
如果使用:
/*Switch.h*/
class CSwitch : public CDeviceEntity { DECLARE_DYNAMIC(CSwitch) }
and
/*Switch.cpp*/
IMPLEMENT_DYNAMIC(CSwitch, CDeviceEntity)
/*EndSystem.h*/
class CEndSystem : public CDeviceEntity { DECLARE_DYNAMIC(CEndSystem) }
and
/*EndSystem.cpp*/
IMPLEMENT_DYNAMIC(CEndSystem, CDeviceEntity)
"DYNAMIC_DOWNCAST
" 根据 class CEndSystem
或 class CSwitch<返回
NULL
或 not NULL
/代码>.
"DYNAMIC_DOWNCAST
" returns NULL
or not NULL
according to class CEndSystem
or class CSwitch
.
为什么DECLARE_DYNAMIC
"和IMPLEMENT_DYNAMIC
"对于DYNAMIC_DOWNCAST
"是必需的?
Why "DECLARE_DYNAMIC
" and "IMPLEMENT_DYNAMIC
" are nessary for "DYNAMIC_DOWNCAST
"?
/*Algorithm.h*/
static int getESNum();
/*Algorithm.cpp*/
int CAlgorithm::getESNum()
{
int count = 0;
CDeviceEntity* dev = NULL;
for (int i = 0; i < topo->nodeNum; i++)
{
dev = topo->headList[i]->node;
if ( DYNAMIC_DOWNCAST( CEndSystem, dev ) != NULL )
{
count++;
}
}
return count;
}
/*Algorithm.h*/
static int getSWNum();
/*Algorithm.cpp*/
int CAlgorithm::getSWNum()
{
int count = 0;
CDeviceEntity* dev = NULL;
for (int i = 0; i < topo->nodeNum; i++)
{
dev = topo->headList[i]->node;
if ( DYNAMIC_DOWNCAST(CSwitch, dev) != NULL )
{
count++;
}
}
return count;
}
并且在保存文档时会以序列化方式调用函数.
And the functions are called in serialization when saving the document.
推荐答案
DYNAMIC_DOWNCAST 是对你在 RTTI 信息可从编译器获得.转换信息是使用宏 DECLARE_DYNAMIC 和 IMPLEMENT_DYNAMIC 创建的,它们使用类 CRuntimeClass 来确定转换是否有效.
DYNAMIC_DOWNCAST is a throw back to how you used to have to do dynamic casting before RTTI information was available from the compiler. The casting information is created using the macros DECLARE_DYNAMIC and IMPLEMENT_DYNAMIC which use the class CRuntimeClass to decide if the cast is valid.
DYNAMIC_DOWNCAST 只是这样做:
DYNAMIC_DOWNCAST simply does this:
CObject* AFX_CDECL AfxDynamicDownCast(CRuntimeClass* pClass, CObject* pObject)
{
if (pObject != NULL && pObject->IsKindOf(pClass))
return pObject;
else
return NULL;
}
DECLARE_DYNAMIC 宏添加了以下代码:
The DECLARE_DYNAMIC macro adds this code:
#define DECLARE_DYNAMIC(class_name)
protected:
static CRuntimeClass* PASCAL _GetBaseClass();
public:
static const CRuntimeClass class##class_name;
static CRuntimeClass* PASCAL GetThisClass();
virtual CRuntimeClass* GetRuntimeClass() const;
添加 IMPLEMENT_DYNAMIC 添加此代码:
Add IMPLEMENT_DYNAMIC adds this code:
#define IMPLEMENT_RUNTIMECLASS(class_name, base_class_name, wSchema, pfnNew, class_init)
CRuntimeClass* PASCAL class_name::_GetBaseClass()
{ return RUNTIME_CLASS(base_class_name); }
AFX_COMDAT const CRuntimeClass class_name::class##class_name = {
#class_name, sizeof(class class_name), wSchema, pfnNew,
&class_name::_GetBaseClass, NULL, class_init };
CRuntimeClass* PASCAL class_name::GetThisClass()
{ return _RUNTIME_CLASS(class_name); }
CRuntimeClass* class_name::GetRuntimeClass() const
{ return _RUNTIME_CLASS(class_name); }
#define IMPLEMENT_DYNAMIC(class_name, base_class_name)
IMPLEMENT_RUNTIMECLASS(class_name, base_class_name, 0xFFFF, NULL, NULL)
我想很少有人仍然将它用于新项目,而是更喜欢 C++ 标准 dynamic_cast<>
调用(以及 static_cast
和 reinterpret_cast
).
I imagine few people still use this for new projects, instead preferring the C++ standard dynamic_cast<>
call (along with static_cast
and reinterpret_cast
).
相关文章