为何C++类内创建对象无法直接使用构造函数调用语法?
问题原因解析
这是C++语法中的**最令人头疼的解析(Most Vexing Parse)**导致的差异,核心是编译器在不同上下文里的语法解析规则不同:
类成员声明区域的
Class2 obj(35);为何报错?
在Class1的类体({}内部,非成员函数的函数体)中,编译器会优先将Class2 obj(35);解析为成员函数声明:返回值类型为Class2,函数名为obj,参数列表里是一个类型为int、名为35的参数。但参数名不能是数字常量,因此触发expected identifier before '(' token和expected ',' or '...' before numeric constant的编译错误。Class2 obj = Class2(35);为何正常?
这种写法属于拷贝/移动初始化,等号的存在明确告诉编译器这是在初始化成员变量,而非声明函数。编译器会先构造临时对象Class2(35),再用它初始化obj(C++11及之后会优化为直接构造,避免临时对象开销),完全不存在解析歧义,因此编译通过。main函数中
Class2 obj(35);为何正常?
在函数体的执行语句块内,C++不允许声明嵌套函数,编译器不会将该语句解析为函数声明,而是直接识别为对象的直接初始化操作,因此编译正常。
额外补充:你也可以用列表初始化语法Class2 obj{35};来替代,这种写法在类成员声明区域也不会触发解析歧义,同样能正常编译。
内容的提问来源于stack exchange,提问作者BadHellie
相关产品推荐
相关产品推荐

