【问题标题】:Function template overloading and ambiguity函数模板重载和歧义
【发布时间】:2021-07-24 06:07:23
【问题描述】:

代码取自 Partial template function specialization with enable_if: make default implementation 。我期待对dummy(5) 的调用在“通用”和“整体”重载之间是模棱两可的,因为在这两种情况下T 都被推断为int。在这两种情况下,第二个参数都解析为 void。他们在dummy(5) 的调用中不是同样“排名”吗?编译器如何选择“通用”版本?

#include <iostream>

template<typename T, typename Enable = void>
void dummy(T t)
{
  std::cout << "Generic: " << t << std::endl;
}


template<typename T, typename std::enable_if<std::is_integral<T>::value>::type>
void dummy(T t)
{
  std::cout << "Integral: " << t << std::endl;
}


template<typename T, typename std::enable_if<std::is_floating_point<T>::value>::type>
void dummy(T t)
{
  std::cout << "Floating point: " << t << std::endl;
}

int main() {
  dummy(5); // Print "Generic: 5"
  dummy(5.); // Print "Generic: 5"
}

【问题讨论】:

    标签: c++ c++11 templates


    【解决方案1】:

    无法调用“积分”重载,因为无法推断第二个模板参数。 (注意typename std::enable_if&lt;std::is_integral&lt;T&gt;::value&gt;::type是在T是整数类型的时候,试图decalre一个类型为void的非类型模板参数,这是无效的。)

    如果您将类型更改为指针(作为非类型模板参数)并为其提供默认参数(如“通用”重载,它使用默认参数void 声明类型模板参数)然后调用将模棱两可。

    template<typename T, typename std::enable_if<std::is_integral<T>::value>::type* = nullptr>
    void dummy(T t)
    {
      std::cout << "Integral: " << t << std::endl;
    }
    

    【讨论】:

    • @sdp 他们不一样。 typename Enable = void 正在声明一个带有默认参数 void 的类型模板参数。当T 为整数类型时,typename std::enable_if&lt;std::is_integral&lt;T&gt;::value&gt;::type 正在尝试对类型为 void 的非类型模板参数进行 decalre,这是无效的。
    • @sdp 尝试删除“通用”重载,您会看到根本不会调用“整体”重载。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-08-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多