使用typename参数时,模板参数推导/替换失败

时间:2017-11-05 01:30:59

标签: c++ function templates parameters traits

我有以下代码,它定义了一个模板结构W,它根据模板参数将T类型导出到W

#include <iostream>
using namespace std;

template <unsigned N>
struct Y {};

template <unsigned N>
struct W {
  using T = Y<N>;
};

然后我定义了这个模板函数来查看这个类型T

template <unsigned N>
void foo (const typename W<N>::T& in) {
  //--
}

这里的问题是,如果我尝试使用导出为main的其中一种类型从T调用此函数,则它不会编译。例如,如果我写

int main() {
  Y<2> y;
  foo(y);
  return 0;
}

我收到一个说

的编译器错误
  

模板参数扣除/替换失败:

     

无法推断出模板参数

这里发生了什么?

1 个答案:

答案 0 :(得分:1)

C ++编译器无法解决这个问题的原因与模板特化有关。例如,假设您专门设置W结构模板,如下所示:

template <> struct W<137> {
    using T = Y<0>; // Not Y<137>
};

现在,假设您调用foo,传入Y<0>作为参数。编译器应该推导出什么作为N的数值?它可能为零,因为W<0>T定义为Y<0>。但它可以很容易地成为137,因为W<137>也将T定义为Y<0>

更一般地说,C ++永远不会尝试基于内部类型之一来推断外部模板的模板参数类型,正是由于上面显示的原因