Reputation: 2936
The code below is OK:
template <class T>
std::enable_if<std::is_atomic<T>::value, bool>
foo(T t) { return true; }
template <class T>
std::enable_if<tmp::is_sequence<T>::value, bool>
foo(T t) { return false; }
int main(void){
foo(1); // return true
auto std::vector<int> a{2};
foo(a); // return false
}
But when I use a class to bundle them, it can not be compiled:
template <class T>
class test {
public:
std::enable_if<std::is_atomic<T>::value, bool>
foo(T t) { return true; }
std::enable_if<tmp::is_sequence<T>::value, bool>
foo(T t) { return false; }
};
int main(...) {
test<int> obj;
obj.foo(1);
test<std::vector<int>> obj2;
std::vector<int> tmp{2};
obj2.foo(tmp);
}
clang++ print:
error: functions that differ only in their return type cannot be overloaded
So I write something to cheat to the compiler(add an S in second foo
):
template <class S>
std::enable_if<tmp::is_sequence<T>::value, bool>
foo(T t) { return false; }
It still can not work:
error: no type named 'type' in 'std::enable_if<false, bool>'
How can I make it work in a class?
Upvotes: 0
Views: 416
Reputation: 1277
You forgot to add ::type after enable_if: (see enable_if)
template <class T> std::enable_if<std::is_atomic<T>::value, bool>::type
foo(T t) { return true; }
Upvotes: 1
Reputation: 361
If you really want to do what you're doing, the classic idiom is to introduce a fake SFINAE argument with a default value:
bool foo(T t, std::enable_if<..., void*> = nullptr) { ... }
Upvotes: 0
Reputation: 55897
Both member-functions should have different template parameter (following will work ok)
template <class T>
class test {
public:
template<typename U>
typename std::enable_if<std::is_atomic<U>::value, bool>::type
foo(U t) { return true; }
template<typename U>
typename std::enable_if<tmp::is_sequence<U>::value, bool>::type
foo(U t) { return false; }
};
Upvotes: 0