繁体   English   中英

Function 模板重载解析,依赖和非依赖参数

[英]Function template overload resolution, dependent and non-dependent parameters

给定以下程序

#include <iostream>

template<class T> struct id { using type = T; };

template<class T1, class T2>
int func(T1, T2) { return 0; }

template<class T1, class T2>
int func(typename id<T1>::type, typename id<T2>::type) { return 1; }

int main()
{
    std::cout << func<int, int>(0, 0) << std::endl;
}

GCC 和 Clang 都为该程序打印1 这个程序是否保证按标准打印1

我试图在这里找到答案,但无法破译。 看起来 function 模板可能是等效的,因此会破坏 ODR,但我不确定。

是否将第二个 function 模板更改为

template<class T>
using id_type = typename id<T>::type;

template<class T1, class T2>
int func(id_type<T1>, id_type<T2>) { return 1; }

做出改变?

这是沼泽标准的部分排序。 我们将唯一类型替换为 function 模板之一,并尝试根据它推断出另一个。 双向进行,如果推论只在一个方向上成功,我们有一个命令。 如果您想阅读神秘的规则,请参阅 [temp.func.order] 和 [temp.deduct.partial]。

所以在这里,

  • T1=U1, T2=U2代入第一个重载的 function 类型产生int f(U1, U2); 我们可以由此推断出第二次重载中的T1T2吗? 不; 两者都在非推断的上下文中。 因此,推演失败。
  • T1=U1, T2=U2代入第二个重载会产生int f(id<U1>::type, id<U2>::type) (这是在定义上下文中进行的,因此我们不能进一步代入id -某处可能有专业化)。 我们可以由此推断出第一次重载中的T1T2吗? 是的,通过推导T1 = id<U1>::typeT2 = id<U2>::type 扣分成功。

由于推导只在一个方向上成功——从转换后的第二个推导第一个——第二个比第一个更专业,并且优先被重载决议挑选。

别名模板案例没有任何改变。


这些模板既不等价,也不在功能上等价。

以下func重载

// Denote as overload F. template<class T1, class T2> int func(typename id<T1>::type, typename id<T2>::type) { return 1; }

比下面的func重载更专业

// Denote as overload G. template<class T1, class T2> int func(T1, T2) { return 0; }

因此,前者是通过重载决议选择的。


(以下所有 ISO 标准参考参考N4659:2017 年 3 月 Kona 后工作草案/C++17 DIS

funcGF重载的部分排序受以下约束:

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM