Use template parameter in preprocessor directive?

Is it possible to use a non-type constant template parameter in a preprocessor directive? Here is what I mean:

template <int DING> struct Foo { enum { DOO = DING }; }; template <typename T> struct Blah { void DoIt() { #if (T::DOO & 0x010) // some code here #endif } }; 

When I try this with something like Blah<Foo<0xFFFF>> , VC ++ 2010 complains about inconsistent parentheses in the line where we are trying to use #if . I assume that the preprocessor really knows nothing about templates, and this kind of thing is simply not in its area. What to say?

+6
c ++ c-preprocessor templates preprocessor-directive
source share
3 answers

No, It is Immpossible. The preprocessor is pretty dumb and it doesn't know the structure of your program. If T::Doo not defined in the preprocessor (and this cannot be, due to :: , it cannot evaluate this expression and will fail.

However, you can rely on the compiler to do the smart thing for you:

  if (T::Doo & 0x010) { // some code here } 

Constant expressions and dead branches are optimized even with lower optimization settings, so you can safely do this without any utilities.

+11
source share

which members are available in T depends on which bits are set in T::DOO

It seems to me that T::DOO acts as a subclass identifier. Therefore, I think your Foo and related classes should be subclasses of the class, which ensures that DOO defined.

Key: why should you use a bit field?

+2
source share

Not sure if this applies to your situation, but different cases can be distinguished using the template classes. For example: (using a modified version of your code above)

 template <typename T, int N> struct Blah { void DoIt() { // normal DoIt() code } }; template <typename T> struct Blah<T,5> { void DoIt() { // special DoIt() code for only when N==5 } }; 
+1
source share

All Articles