考虑以下 C++ 程序
#include <cwchar>
#include <cwctype>
#include <string>
#include <functional>
template <typename Ty>
struct Tokenize {
Ty m_delim;
Tokenize(Ty& delim):m_delim(delim){}
};
int main() {
std::function<bool (wchar_t)> foo = iswdigit; //Compiles fine
Tokenize<std::string >(std::string("")); //Compiles fine
Tokenize<std::function<bool (wchar_t)> >(foo); // Fails
return 0;
}
尝试使用 VC++ 进行编译时,因编译器错误而失败
error C2371: 'foo' : redefinition; different basic types
error C2512: 'Tokenize<Ty>' : no appropriate default constructor available
看起来它试图重新定义 foo,但不知道究竟如何
注意 仔细检查会发现编译器认为
Tokenize<std::function<bool (wchar_t)> >(foo)
构造一个 Tokenize<std::function<bool (wchar_t)> >
类型的对象使用默认参数,即
Tokenize<std::function<bool (wchar_t)> > foo
但问题仍然是为什么?
最佳答案
你习惯于看到这样的代码:
T(arg1, arg2)
为了创建 临时 T
类型。您习惯于在表达式中看到这一点,例如:
f(T(arg1, arg2))
你也见过它有一个参数:
f(T(arg1))
但是,当您假定的临时创建是一行代码中的完整 语句时,它在句法上与声明没有区别。
即:
T(arg1);
等同于:
T arg1;
如果一段代码可能是一个声明或一个表达式,它始终是一个声明。这本质上是 most vexing parse 的一个示例.
您可以使用 ()
来消除歧义,强制将语句读作表达式:
(T(arg1));
但我通常会问,为什么您觉得有必要在自己的行上创建一个临时的,然后您什么都不做。
关于c++ - 尝试使用 std::function 实例化模板时出现错误 C2371,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14921474/