On 2012-03-04 15:10, Daniel Kr?gler wrote:
Ensure that your primary template is a slightly worse match (even in the
absence of constraints), then add constrained overloads. Here is an
example of what I'm thinking of:
#include<type_traits>
#include<iostream>
struct Animal {};
struct Dog : Animal {};
struct Fruit {};
struct Apple : Fruit {};
struct Other {};
template<class T>
typename std::enable_if<std::is_pointer<T>::value>::type
do_action(T ptr) { std::cout<< "generic"<< std::endl; }
template<class T>
inline void action(T* ptr) { do_action(ptr); }
template<class T>
typename std::enable_if<std::is_base_of<Animal, T>::value>::type
do_action(T* ptr) { std::cout<< "animals"<< std::endl; }
template<class T>
typename std::enable_if<std::is_base_of<Fruit, T>::value>::type
do_action(T* ptr) { std::cout<< "fruits"<< std::endl; }
Thank you very much, that works indeed.
One question I have is: is there any reason you introduced an extra level
of indirection, namely do_action? That is, wouldn't this ...
template<typename T>
typename std::enable_if<std::is_pointer<T>::value>::type
action(T ptr) { std::cout<< "generic"<< std::endl; }
template<typename T>
typename std::enable_if<std::is_base_of<Animal, T>::value>::type
action(T* ptr) { std::cout<< "animals"<< std::endl; }
template<typename T>
typename std::enable_if<std::is_base_of<Fruit, T>::value>::type
action(T* ptr) { std::cout<< "fruits"<< std::endl; }
... work as well? I tried it, and it seemed to work.
Sure. The reason why I suggested the indirection was just to provide a
may be astonishing to see this construction). It would suffice to add a
corresponding documentation to explain this, though.
[ comp.lang.c++.moderated. First time posters: Do this! ]