反射2--[仿照Qt反射接口]
main.cpp
#include "register.h" #include "object.h" using namespace std; /* 模仿Qt反射接口,使用函数模版。 可以与 宏定义define ## 进行对比。 感觉不错的。 其中使用 int类型id,完全是为了遵照Qt反射的风格。 */ int main(void) { //类型注册 Register<CObjA>("CObjA"); Register<CObjB>("CObjB"); //反射出相同类型,不同对象对象 int ida1 = MetaType::Type("CObjA"); IObj* pobja1 = (IObj*)(MetaType::Create(ida1)); pobja1->Welcome(); int ida2 = MetaType::Type("CObjA"); IObj* pobja2 = (IObj*)(MetaType::Create(ida2)); pobja2->Welcome(); int idb = MetaType::Type("CObjB"); IObj* pobjb = (IObj*)(MetaType::Create(idb)); pobjb->Welcome(); return 0; }
register.h
#ifndef _REGISTER_H_ #define _REGISTER_H_ #include <iostream> #include <string> #include <map> using namespace std; typedef void* (*FCreate)(void); extern map<int, FCreate> g_idFunMap; extern map<string, int> g_stringIdMap; //创建对象 template<class classname> void* CreateFun() { return new classname; } //注册 template<class classname> int Register(string strclassname)
{ //id可以随意定义,不重复就可以,可以根据字符串进行匹配id算法 int id = g_idFunMap.size(); id++; g_idFunMap[id] = CreateFun<classname>; g_stringIdMap[strclassname] = id; return 0; } class MetaType { public: MetaType(); virtual ~MetaType(); static int Type(string strtype); static void* Create(int iid); }; #endif
register.cpp
#include "register.h" map<int, FCreate> g_idFunMap; map<string, int> g_stringIdMap; MetaType::MetaType() { } MetaType::~MetaType() { } int MetaType::Type(string strtype) { return g_stringIdMap[strtype]; } void* MetaType::Create(int iid) { return (*(g_idFunMap[iid]))(); }
object.h
与反射1中的代码,对象代码类似
#include <iostream> #include <string> using namespace std; class IObj { public: virtual void Welcome() = 0; }; class CObjA : public IObj { public: CObjA() {} virtual ~CObjA() {} void Welcome() { cout << "CObjA "<< this <<endl; } }; class CObjB : public IObj { public: CObjB() {} virtual ~CObjB() {} void Welcome() { cout << "CObjB "<< this <<endl; } }; #endif