在类模板中推导模板成员函数

Kam*_*jii 6 c++ templates

在下面的例子中为什么不能Tfn签名中推断出来?

template<int I>
struct Class {
    template<typename T>
    Class &operator <<( void (*)(const Class<I> &, const T &) ) { return *this; }
};

struct Ot { };

template<int I>
void fn(const Class<I> &, const Ot &) { }

int main() {
    Class<1>() << fn;
}
Run Code Online (Sandbox Code Playgroud)

相比之下,以下operator<<不是常规成员的示例是合法的:

template<int I>
struct Class {
    Class &operator <<( void (*)(const Class<I> &) ) { return *this; }
};

struct Ot { };

template<int I>
void fn(const Class<I> &) { }

int main() {
    Class<1>() << fn;
}
Run Code Online (Sandbox Code Playgroud)

Lui*_*man 0

归根结底,函数模板的模板参数可以显式指定,也可以从传递给函数的参数中推导出来。

在您的示例中,编译器无法确定 的模板参数,fn因为在对 的调用中没有参数传递给它Class<1>::operator<<()。因此,您必须明确指定它:(fn<1>或您想要的任何内容)。一旦完成此操作,并且的类型明确,编译器就可以推导出from的第二个参数类型(即 fn<1>)fn的类型。TClass<1>::operator()

换句话说,类型fn不清楚。您可以将 fn<2> 传递给 Class<1>::operator<<()。考虑这段代码:

Class<1> << fn<2>;   // fn<2> is not fn<1>
Class<1> << fn<1>;   // OK too, of course
Class<1> << fn;      // error! fn<?>
Run Code Online (Sandbox Code Playgroud)