为何该constexpr表达式报错?同代码两行表现差异解析
问题:constexpr对象初始化报错的疑惑
以下C++代码中,第2行的constexpr声明未报错,但第1行出现报错。虽然randGen()返回固定整数10,但编译器却无法在编译期计算它,这是为什么?
#include <iostream> using namespace std; class ComplexNum{ public:constexpr ComplexNum(int _r=0,int _i=0):r(_r),i(_i){} private: int r,i; }; int randGen(){ return 10; } constexpr int numGen(int i,int j){ return i+j; } int main() { constexpr int i=10,j=20; constexpr ComplexNum c3(randGen(),randGen()); //line 1 constexpr ComplexNum c4(numGen(i,j),numGen(i,j));//line 2 return 0; }
解答
constexpr要求初始化表达式必须是常量表达式,这不是看函数返回值是否固定,而是看函数本身的属性是否符合常量表达式的要求:
randGen()是普通的非constexpr函数,哪怕它返回固定值,C++标准也不允许在常量表达式上下文里调用它。编译器不会去推断函数运行时的行为,只会严格依据函数声明——只有被标记为constexpr的函数,才能在编译期求值场景中被调用。numGen()被明确声明为constexpr,且它的实现仅依赖传入的常量参数做简单计算,完全符合常量表达式的规则,因此可以用于初始化constexpr对象。
另外,ComplexNum的constexpr构造函数本身是合法的,但它的参数必须是常量表达式才能用来初始化constexpr对象。第1行的randGen()不满足这个条件所以报错,第2行的numGen(i,j)是合法常量表达式,因此能通过编译。
内容的提问来源于stack exchange,提问作者Akash Kp
相关产品推荐
相关产品推荐

