Tuesday, December 25, 2012

Compile time reflection in C++

 *This is an example of the wasted brain cycles C++ forces on us because it lacks common sense stuff like modules & compile time reflection*

Unfortunately C++ does not have reflection--compile time or otherwise. It might be added in C++17, but I needed it *now*.

 So I wrote a macro using the Boost Preprocessor library to generate compile time reflection data within a class.

 A Reflected object looks like this:
 After macro evaluation this generates an embedded type called "Reflection".
 The Reflection structure contains N sub types labled [Member1 - MemberN], and an enum indicating how many members are present.

 Each Member structure then contains the following data.

1. The type: (Member::type)
2. Access to member pointer (Member::GetMemberPtr())
3. Access to name of the reflected member (Member::GetName())
4. A type which indicates if the member is a function or variable, and if it is static or not(Member::member_class)
4. Optional meta data(basically user defined attributes). (Member::meta)

 The meta tags can be optionally attached like so:

           ((_member)(Serialize)(Replicate)) //Serialize and Replicate being types you have declared 

 You then need some compile time functionality to walk this and generate something useful out of it.

Dealing with inherited base types is not difficult, you just need to add a type list which lists any base types, and then have your evaluation functions walk the full hierarchy.

 Here is a link to the code if you are interested: reflection

 Uses decltype and auto so some C++11 conformance is required.

1 comment: