c++ - 基类的模板函数重载

标签 c++ function templates overloading

<分区>

我如何强制编译器为基类选择模板函数重载?

举个例子说明问题

#include <iostream>

class A
{};

class B : public A
{};

template <class T>
void f (const T& t)
{
    std::cout << "Generic f" << std::endl;
}

void f (const A& a)
{
    std::cout << "Overload for A" << std::endl;
}

template <class T>
void call_f (const T& t)
{
    f (t);  
}

int main() 
{
    call_f (10);
    call_f (A());
    call_f (B());

    return 0;
}

它产生输出

Generic f
Overload for A
Generic f

为什么编译器不接收 f (const A&)在第三种情况下? UPD:好的,这个很清楚void f<B> (const B&)优于void f (const A&) ,但我仍在寻找第二个问题的答案。

是否有可能强制它这样做而不将 B 转换为 A

最佳答案

使用 call_f(B())导致调用与模板版本最匹配的`f()。对于非模板版本,需要进行转换。结果,选择了模板。如果模板和非模板是同样好的选择,那么非模板将是首选。

如果要调用非模板,则需要将模板设为非选项。例如,模板可以这样实现

#include <type_traits>
template <class T>
typename std::enable_if<!std::is_base_of<A, T>::value>::type f(T const&)
{
    std::cout << "Generic f\n";
}

如果不能使用 C++11,您可以实现 std::is_base_of<...> 的一个版本,使用来自 Boost 的版本或者使用简单的调度:

struct true_type {};
struct false_type {};

true_type A_is_base_of(A const*) { return true_type(); }
false_type A_is_base_of(void const*) { return false_type(); }

template <class T>
void f (T const&, false_type)
{
    std::cout << "Generic f\n";
}

void f (A const&, true_type)
{
    std::cout << "Overload for A\n";
}

template <class T>
void call_f (const T& t)
{
    f (t, A_is_base_of(&t));  
}

关于c++ - 基类的模板函数重载,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24290678/

相关文章:

c++ - X 请求失败错误 : BadValue (integer parameter out of range for operation)

c++ - OpenCV:如何传递 cv::Ptr 作为参数?

javascript - 在 javascript 中,window.function(){} 和 var variable = function 有什么区别?

c++ - 我有几个函数重载,每个函数重载都有一个不同的子类;如何检查给定对象使用哪个函数?

c++ - 通过 C API 实例化 Lua 对象

c - 如何在另一个函数中访问这个二维数组?

ruby - ruby 中的无效功能

c++ - 通过重载进行部分模板特化

C++ 将方法指针作为模板参数传递

C++ std::vector 带有指向模板类的指针