John Maddock wrote:
there's an opportunity here to remove all that obfuscation and crud and
produce something that's actually halfway readable and maintainable.
Just on the topic of maintenance:
A C++17 style voider works with GCC 3.2 and later, VS8 and later and
various HP aCC, Sun Studio, Intel and other compilers listed here:
https://open.cdash.org/index.php?project=CMake&date=2015-01-05
Only VS 7.1 chokes on it.
What's a C++ 17 style voider?
See
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n3911.pdf
https://www.youtube.com/watch?feature=player_detailpage&v=a0FliKwcwXE#t=1740
Even if using VS8, GCC3.2 etc you can still do this:
template<typename>
struct voider { typedef void type; };
struct true_type
{
enum { value = true };
};
struct false_type
{
enum { value = false };
};
template
struct HasSecondType : false_type {};
template<typename T>
struct HasSecondType : true_type {};
template
struct PointerHelper {};
template
struct HasSomeMemberFunc : false_type {};
template<typename T>
struct HasSomeMemberFunc >::type> :
true_type {};
template
struct HasSomeMemberData : false_type {};
template<typename T>
struct HasSomeMemberData >::type> :
true_type {};
struct A
{
int somemember(int);
int somemember(double);
double data;
};
struct B
{
int data;
double otherData;
};
template<bool b>
class myStaticAssert;
template<>
class myStaticAssert<true> {};
#define My_Join(A, B) My_Joiner(A, B)
#define My_Joiner(A, B) A ## B
#define My_StaticAssert(cond, message) \
enum {My_Join(assert, __LINE__) = sizeof(myStaticAssert<cond>)};
My_StaticAssert(HasSomeMemberFunc<A>::value, "");
My_StaticAssert(!HasSomeMemberFunc<B>::value, "");
My_StaticAssert(HasSomeMemberData<A>::value, "");
My_StaticAssert(!HasSomeMemberData<B>::value, "");
I'll leave it as an excercise for you to macro-ize the HasSomeMemberData etc
structs.
Thanks,
Steve.