
Marco Costalba wrote:
Problem I found is that compile-time info sometime is not enough.
As example if you have something like this:
template<int n, typename arg> void dispatch_on_value(std::string const& s, arg const& a) { if ( s == some_string(n) )
/* calls member foo() on the class returned by get_a_class */ return get_a_class<n>().foo(a);
return dispatch_on_value<n-1>(s, a); // try with next one }
In this simple example template function get_a_class<int>() returns different classes according to parameter <int>.
On the returned classes member foo() with argument 'a' is called.
The problem is that not all the classes returned by get_a_class<int> could have a member foo(), or also if they have, signature of foo() could be different for each class, so that foo(a) could be ill formed for some of them.
Then, as I said, you could provide compile-time information to know what are all the members of a class and all their signatures. template<typename T> struct reflection { }; template<> struct reflection<YourClass> { typedef boost::mpl::map< boost::mpl::pair< boost::mpl::vector_c<char, 'f', 'o', 'o'>, boost::mpl::vector< boost::mpl::pair< return_type, boost::mpl::vector<> /* argument types */ > boost::mpl::pair< // another overload another_return_type, boost::mpl::vector<> /* other argument types */ > > > type; }; Then you write a meta-function to check whether the class has a member function with the corresponding name and signature and branch with SFINAE. Of course here the reflection format is quite primitive. It should be improved to represent all of member variables, member functions, typedefs, static variables, static functions. Also I don't really see how to expose template signatures.