einpoklum
einpoklum

Reputation: 132260

Achieving an SFINAE-like effect in an if-else block

I would like to be able to write something like

template <typename T> void foo() {
    // ...
    if (is_nice<T>::value) {
        bar_which_is_defined_only_for_nice_types<T>();
    }
}

However, when I try to compile this (g++ 4.9.3, no optimization) I get a complaint about bar_which_is_defined_only_for_nice_types. How can I achieve the desired effect without resorting to 2 definitions of foo()?

Upvotes: 1

Views: 357

Answers (1)

Praetorian
Praetorian

Reputation: 109289

You can tag dispatch based on is_nice<T>

#include <type_traits>

template<typename T>
struct is_nice : std::false_type {};
template<>
struct is_nice<int> : std::true_type {};

template<typename T>
void do_nice_things(std::true_type)
{
    bar_which_is_defined_only_for_nice_types<T>();
}

template<typename T>
void do_nice_things(std::false_type)
{
}

template <typename T>
void foo()
{
    do_nice_things<T>(is_nice<T>{});
}

Upvotes: 8

Related Questions