C++中的模板:(F-)有界多态性

Templates in C++: (F-)bounded polymorphism

本文关键字:多态性 C++      更新时间:2023-10-16

我已经在intrnet上检查了一段时间,并且没有找到我的问题的任何答案。我想知道C++是否支持有界多态性和/或 F 有界多态性。

例如,在Java中,程序员可以这样做(有界多态性):

<T extends Car> void startEngine(T c) {/*body method*/}

和这个(F有界多态性):

<T extends Comparable<T>> void compareWith(T c) {/*body method*/}

C++有什么等价物吗?

谢谢!

<T extends Car> void startEngine(T c) {}

在C++中,相当于上述内容是这样的:

template<typename T, typename Unused= typename std::enable_if<std::is_base_of<Car,T>::value>::type>
void startEngine(T c) {}

好吧,语法很丑陋,但你可以用别名让它更好一点:

//first define a (reusuable) alias
template<typename D, typename B>
using extends = typename std::enable_if<std::is_base_of<B,D>::value>::type;
//then your code would look like this
template<typename T, typename Unused=extends<T,Car> >
void startEngine(T c) 
{
}

或者你可以使用 static_assert ,正如另一个答案所解释的那样。但std::enable_ifstatic_assert并不等同。虽然static_assert让您有机会生成良好的错误消息,但std::enable_if可以帮助您解决重载问题,这意味着仅当CarT的基础时,才会调用上述函数,否则将选择/考虑其他重载(如果有)。使用static_assert,这是不可能的:它只是失败并停止 - 它不会进一步寻找过载。

同样

//then your code would look like this
template<typename T, typename Unused=extends<T,Comparable<T>> >
void compareWith(T c) 
{
}

这种技术被称为:

  • 荸荠属

希望有帮助。

在 C++11 中,您可以使用static_assert和类型特征来检查模板参数是否是从特定类派生的类。例如:

#include <type_traits>
class Base {};
class Derived : Base {};
class Other {};
template<class T>
void foo(T t)
{
    static_assert(std::is_base_of<Base, T>::value, "T must be a class derived from Base");
}
int main()
{
    foo(Derived()); // ok
    foo(Base()); // ok
    foo(Other()); // error: static assertion failed: T must be a class derived from Base
}