函数模板和多态性

function template and polymorphisme

我正在尝试获取一个用于项目(对象描述)的简单示例,并且我想避免一些额外的编码,如旁边所示, 所以我的代码在这里:

// My function template foo : i call foo on all my object i want to describe ...
template<class T, class = void>
void foo(T &r);

// I tried this but i the compiler never use this function ...
template<class T, typename std::enable_if<std::is_base_of<Base,   T>::value>::type>
void foo(T &r)
{
    std::cout << "Base or Derivated" << std::endl;
}

template<> void foo<int, void>(int &r)
{
    std::cout << "int" << std::endl;
}

template<> void foo<double, void>(double &r)
{
    std::cout << "double" << std::endl;
}

template<> void foo<Base, void>(Base &r)
{
    std::cout << "Base" << std::endl;
}
// in other librairies we can found other specialization 
template<> void foo<OtherClass, void>(OtherClass &r)
{
    std::cout << "OtherClass" << std::endl;
}

和主要的:

int main()
{
    int a(1);
    double b(5.5);
    Base c;
    Derivated d;
    foo(a); // OK 
    foo(b); // OK
    foo(c); // OK
    foo<Base>(d); // OK
    foo(d);  // Compile but erreor at linking 
    return 0;
}

所以实际上我从 Base 派生了很多 class ...我不想创建所有的专业化,加上其他约束(库依赖等..)。 我想知道有没有办法调用:

foo(d); // decltype(d) = Derivated : public Base

而不是:

foo<Base>(d); // decltype(d) = Derivated : public Base

感谢您的帮助

我终于找到了一种“干净的方法来做我想做的事情,我的代码:

template <class T >
typename std::enable_if<std::is_base_of<Base, T>::value, void>::type
foo(T &r)
{
    std::cout << "T is base of Base" << std::endl;
}

template <class T >
typename std::enable_if<!std::is_base_of<Base, T>::value, void>::type
foo(T &r);


template<> void foo(int &r)
{
    std::cout << "int" << std::endl;
}

template<> void foo(double &r)
{
    std::cout << "double" << std::endl;
}

template<> void foo(OtherClass &r)
{
    std::cout << "OtherClass" << std::endl;
}

int main()
{
    int a(1);
    double b(5.5);
    float f(3.3);
    Base c;
    Derivated d;
    OtherClass e;
    foo(a); // OK foo(int) available
    foo(b); // OK foo(double) available
    foo(c); // OK foo(Base) available
    foo(d); // OK foo(Derivated share the same defenition as foo(Base)
    foo(e); // OK foo Other class available
    foo(f); // OK at compiling but error a linking -> no specialization for        foo(float) available
}