C++函数模板偏序机制解析:示例对应的标准规则问询
C++函数模板重载决议:特化优先级判定解析
针对你给出的代码示例,调用foo(array<int, 1>{})时的模板选择逻辑,核心依据是C++标准的**[temp.func.order]章节——该章节定义了函数模板"更特化"的判定规则,核心逻辑是通过双向模板实参推导**验证特化关系:即尝试将一个模板的假设实参代入另一个模板的参数列表,只有当单向推导成功、反向推导失败时,前者才被判定为更特化。
1. 判定#3比#2更特化
按照[temp.func.order]的规则,执行两次推导测试:
- 正向推导(用#3匹配#2):假设#3的模板参数为
T=X,则#3的函数参数是array<X, 1>。将此参数代入#2的参数array<T, N>,可以推导出#2的T=X、N=1,推导成功。 - 反向推导(用#2匹配#3):假设#2的模板参数为
T=Y、N=M(M为任意整数),则#2的函数参数是array<Y, M>。将此参数代入#3的参数array<T, 1>,要求M=1才能匹配,但M是任意值,无法推导出符合要求的固定结果,推导失败。
根据规则,当A能匹配B的参数、但B无法匹配A的参数时,A比B更特化。因此#3比#2更特化。
2. 判定#2比#1更特化
同样执行双向推导测试:
- 正向推导(用#2匹配#1):假设#2的模板参数为
T=Z、N=K,则#2的函数参数是array<Z, K>。将此参数代入#1的参数T,可直接推导出#1的T=array<Z, K>,推导成功。 - 反向推导(用#1匹配#2):假设#1的模板参数为
T=W(任意类型,比如int),则#1的函数参数是W。将此参数代入#2的参数array<T, N>,无法从普通类型W推导出array模板的结构,推导失败。
因此#2比#1更特化。
3. 最终重载决议结果
综合两次判定,三个模板的特化优先级为:#3 > #2 > #1。所以调用foo(array<int, 1>{})时,编译器会选择#3作为匹配的模板。
内容的提问来源于stack exchange,提问作者Jan Schultke
相关产品推荐
相关产品推荐

