Kurt
Kurt

Reputation: 97

C++ compile time checking of type equality in a preprocessor directive

I'd like to check if two POD types are equal at compile time in C++11. I'm trying to #define function names that are appropriate for the Float_T type. Here is what I tried:

#include <type_traits>

using Float_T = double;
// using Float_T = float;

#if is_same<Float_T, double>::value
    #define LOG2  log2
#else
    #define LOG2  log2f
#endif

 g++ complains:  error: extra text after expected end of preprocessing directive
  #if is_same<Float_T, double>::value
                     ^

Can anyone suggest a way to do this?

Upvotes: 1

Views: 518

Answers (1)

Ruks
Ruks

Reputation: 3956

Macros are evaluated when the source code is being parsed, much before compilation kicks in, which is why it is nothing more than a simple copy-paste mechanism. So, doing something like this:

#if is_same<Float_T, double>::value
    #define LOG2  log2
#else
    #define LOG2  log2f
#endif

Is practically impossible since is_same and #if are evaluated at different times during the whole compilation procedure. What you can do is to change the macro into a function, like this:

#include <type_traits>
#include <cmath>

using Float_T = double;

template <typename T = Float_T>
typename std::enable_if<std::is_same<T, double>::value, double>::type LOG2(Float_T const& x) {
    return log2(x);
}

template <typename T = Float_T>
typename std::enable_if<!std::is_same<T, double>::value, float>::type LOG2(Float_T const& x) {
    return log2f(x);
}

// ...

Upvotes: 2

Related Questions