考虑this code:
struct matrix
{
matrix(int a, int b, int c, int d)
: a(a), b(b), c(c), d(d){}
matrix()
: a(0), b(0), c(0), d(0){}
int a, b, c, d;
};
static const matrix mx0;
static const matrix mx1(1,1,1,1);
const matrix& test(bool f)
{
return f ? mx1 : mx0;
}
为什么编译器无法识别并避免生成所有乱码来生成这两个全局静态mx0
和mx1
?
为什么只有当我mark constructors constexpr时,编译器才能在不使用此关键字的情况下执行我期望的操作?请注意,优化启用编译器窗台doesn't generate the same result与code that uses constexpr一样。
答案 0 :(得分:1)
首先让我说这是一个猜测,但(我相信)它是一个受过教育的人。
我不是在C ++标准委员会,但从我在网上阅读和看到的内容我可以告诉你,他们(并且仍然)非常热衷于向后兼容该语言的早期版本。如果允许C ++ 11编译器以静默方式将constexpr
应用于构造函数并初始化const变量,则在C ++ 11下重新编译时会改变现有程序的行为 - 从运行时转为编译 - 时间初始化。一般来说,在语言的更高版本中重新编译时改变程序的行为被视为一件坏事*。
因此,要获得以前不可能的新行为,需要将原始代码更改为以前不合法的C ++。要求新的constexpr
关键字在构造函数(或其他函数)声明上是一种简单有效的方法。
* 当然,每个规则都有例外,例如编译器生成的移动构造函数/赋值运算符,但他们非常小心,除非可证明是良性的,否则不能自动添加这些。