#include <iostream>
#include <stdint.h>
#include <map>
#include <typeinfo>
class RttiCasterBase
{
private:
class RttiRegFactory
{
private:
typedef std::map<std::string, uint32_t> RttiIDMap;
//0 is the bad marker..
uint32_t g_uid;
RttiIDMap rttiIDMap;
RttiRegFactory() :
g_uid(1)
{}
public:
static RttiRegFactory& instance()
{
static RttiRegFactory instance_;
return instance_;
}
uint32_t getID(std::string rttiName)
{
if (rttiIDMap.find(rttiName) != rttiIDMap.end())
return rttiIDMap[rttiName];
rttiIDMap[rttiName] = g_uid;
return g_uid++;
}
};
protected:
static uint32_t lookup(std::string rttiID)
{
return RttiRegFactory::instance().getID(rttiID);
}
public:
RttiCasterBase() {}
virtual ~RttiCasterBase() {}
virtual uint32_t uid() = 0;
virtual std::size_t size() = 0;
virtual std::string rttiID() = 0;
};
template<typename T>
class RttiCasterImp : public RttiCasterBase
{
public:
typedef T Type;
uint32_t uid_;
RttiCasterImp() :
RttiCasterBase()
{
uid_ = RttiCasterBase::lookup(typeid(T).name());
}
~RttiCasterImp() {}
virtual uint32_t uid()
{
return uid_;
}
virtual std::size_t size()
{
return sizeof(T);
}
virtual std::string rttiID()
{
return typeid(T).name();
}
T* cast(void* buf)
{
return reinterpret_cast<T*>(buf);
}
void print(std::ostream& out)
{
out << "uid: " << uid() << std::endl
<< "size: " << size() << std::endl
<< "rttiID: " << rttiID() << std::endl
<< std::endl;
}
};
class A {};
class B { int var; };
class C { char stuff[10]; };
int main(int argc, char const * const *argv)
{
RttiCasterImp<A> InfoA;
RttiCasterImp<B> InfoB;
RttiCasterImp<C> InfoC;
RttiCasterImp<B> InfoD;
InfoA.print(std::cout);
InfoB.print(std::cout);
InfoC.print(std::cout);
InfoD.print(std::cout);
}
Output looks like:
$ a.exe uid: 1 size: 1 rttiID: 1A uid: 2 size: 4 rttiID: 1B uid: 3 size: 10 rttiID: 1C uid: 2 size: 4 rttiID: 1B
No comments:
Post a Comment