С каждым классом пороженным от CObject связывается структура CRuntimeClass, в которой находится информация о классе. Её можно использовать для получения информации об объекте.
struct CRuntimeClass { LPCSTR m_lpszClassName; int m_nObjectSize; UINT m_wSchema; CObject* (PASCAL* m_pfnCreateObject)(); // NULL => abstract class #ifdef _AFXDLL CRuntimeClass* (PASCAL* m_pfnGetBaseClass)(); #else CRuntimeClass* m_pBaseClass; #endif CObject* CreateObject(); BOOL IsDerivedFrom(const CRuntimeClass* pBaseClass) const; void Store(CArchive& ar) const; static CRuntimeClass* PASCAL Load(CArchive& ar, UINT* pwSchemaNum); CRuntimeClass* m_pNextClass; };
Все эти атрибуты легко получить. Пример:
// TestP.cpp : Defines the entry point for the console application. // #include "stdafx.h" #include "afxwin.h" #include "iostream.h" void main() { CFile cf; CRuntimeClass *cr; cr=cf.GetRuntimeClass(); cout << cr->m_lpszClassName << " " << cr->m_nObjectSize << " " << cr->m_wSchema << endl; }
CObject* (PASCAL* m_pfnCreateObject)(); - если поддерживается динамическое создание, то тут хранится указатель на конструктор по умолчанию, иначе NULL.
Определение _AFXDLL позволяет по разному описать класс в зависимости от того с какой версией MFC вы работаете, т.е. динамической или статической.
CRuntimeClass* (PASCAL* m_pfnGetBaseClass)(); - только в динамической версии, указатель на структуру базового класса. Для статической используется CRuntimeClass* m_pBaseClass;.
CObject* CreateObject(); - создание объекта, если он поддерживает динамическое создание.
BOOL IsDerivedFrom(const CRuntimeClass* pBaseClass) const; - проверка является ли класс производным.
Функции Store() и Load осуществляют чтение и сохранение класса в файловый поток.