我的构造函数有问题,但是我没想到这个问题。
如果我尝试像这样初始化我的类,它将起作用并且我得到一个可用的对象:
vector<float> v;
MyClass<2> a(v);
但是,如果我尝试构建类似下面的类(应该是等效的),结果是非常意外的。编译或运行程序时没有错误消息/警告。但是如果你尝试在某个地方使用这个变量并调用它的方法(例如a.doSomething()),它就会崩溃。
我在构造函数中放了一些代码来通知我它是否被使用。事实证明,在这种情况下,构造函数中没有实际执行代码。
MyClass<2> a(vector<float>());
所以我想知道为什么会这样?第二次申报是非法的吗?
编辑:我会发布一些类的代码
template <int x>
class MyClass {
public:
vector<float> v;
MyClass<x>(vector<float> v1) {
v = v1;
}
};
答案 0 :(得分:18)
MyClass<2> a(vector<float>());
这不是变量声明。它是一个名为a
的函数的声明,它返回一个MyClass<2>
对象,并将一个“指向不带参数的函数的指针作为参数,并返回vector<float>
”。混乱?是。这就是所谓的“最令人烦恼的解析”。
您需要额外的括号:
MyClass<2> a((vector<float>()));
^ ^
或者,您可以使用复制初始化:
MyClass<2> a = MyClass<2>(vector<float>());
或者,由于您的构造函数不是explicit
,您可以使用:
MyClass<2> a = vector<float>();
(但是,除非你的意思是vector<float>
个对象可以隐式转换为MyClass<N>
个对象,否则你可能想要构建这个构造函数explicit
。)
一个好的编译器应该警告你这类事情。 Visual C ++警告:
警告C4930:'
MyClass<x> a(std::vector<_Ty> (__cdecl *)(void))
':未调用prototyped函数(是否为变量定义?)
Clang警告说:
警告:括号被解除歧义为函数声明符
MyClass<2> a(vector<float>()); ^~~~~~~~~~~~~~~~~