MSVC中constexpr上下文未调用构造函数体是否符合C++标准?
问题:constexpr上下文构造函数体未执行的兼容性疑问
我尝试向参数为std::vector的结构体构造函数传递初始化列表,在Visual Studio Community中得到了不符合预期的结果。
复现代码如下:
#include <vector> #include <iostream> using namespace std; struct ST { std::size_t size1; std::size_t size2; constexpr ST(std::vector<int> production) : size1(production.size()) { size2 = production.size(); } }; static constexpr auto get_ST() { return ST({ 1, 2, 3 }); } int main() { auto par = get_ST(); std::cout << par.size1 << " " << par.size2 << std::endl; constexpr auto par2 = get_ST(); std::cout << par2.size1 << " " << par2.size2 << std::endl; }
在Visual Studio Community中的输出为:
3 3 3 0
而在GCC中的输出为:
3 3 3 3
从输出可见,MSVC在constexpr上下文未调用构造函数体,请问这是否符合C++标准,还是MSVC的bug?
分析与结论
这是MSVC的bug,不符合C++标准的要求。
根据C++标准,当在常量表达式上下文(比如constexpr变量初始化)中调用constexpr构造函数时,构造函数的完整逻辑必须被执行,包括初始化列表和构造函数体中的代码。在上述代码里,size2 = production.size();属于构造函数体的一部分,在常量表达式求值过程中必须被执行,因此size2应当被正确赋值为3,而非默认初始化的0。
GCC的行为符合标准,而MSVC在constexpr上下文中跳过了构造函数体的执行,这是不符合规范的实现错误。
内容的提问来源于stack exchange,提问作者Aakash Gupta
相关产品推荐
相关产品推荐

