将 constexpr 添加到语言后是不是将变量声明为 const 多余?

Posted

技术标签:

【中文标题】将 constexpr 添加到语言后是不是将变量声明为 const 多余?【英文标题】:Is declaring variables as const redundant after constexpr was added to the language?将 constexpr 添加到语言后是否将变量声明为 const 多余? 【发布时间】:2021-04-24 01:14:03 【问题描述】:

由于关键字constexpr 暗示const 并且它也可以在编译时计算,这是否意味着现在将变量声明为const 没有意义,我们应该始终将它们声明为constexpr

【问题讨论】:

【参考方案1】:

而且它也可以在编译时计算,是不是意味着现在将变量声明为const没有意义,我们应该始终将它们声明为constexpr

并且必须在编译时计算(忽略as-if rule)。

因此,您不能声明 constexpr 使用运行时已知值初始化的变量。但是你可以声明它const

例如:不能声明barconstexpr

int foo;

std::cin >> foo;

constexpr int bar = foo;  // compilation error

但你可以声明它const

int foo;

std::cin >> foo;

const int bar = foo;  // compile

【讨论】:

并且必须计算编译时间。 - 我认为它仍然是可以,因为最终编译器自己决定,没有人 100% 保证所有 constexpr 表达式都将在编译时进行评估 @Johy - 您正在描述假设规则。是的:编译器可以在运行时计算constexpr 变量的值,如果这不会改变程序的行为的话。在答案中添加了一点免责声明。【参考方案2】:

不,一点也不。

constexpr 表示“常量表达式”,如 [可能] 静态已知,如“[可能] 在编译时已知”。

const 表示“初始化后无法更改”。

这些是完全不同的概念。例如,const 对象可以使用运行时值进行初始化。

constexpr 可以暗示 const,但const 肯定不暗示constexpr

(因此,我认为constexpr 是一个非常令人困惑的名字。)

【讨论】:

“但 const 肯定不暗示 constexpr” - 除了涉及整数类型和枚举的烦人的小旧花絮。它可能有点像薛定谔的常数。 constexpr 可以暗示 const - 你的意思是有些情况下 constexpr 变量可以用另一个值重新分配?我虽然那个 constexpr vars 总是 const @Johy 我的意思是constexpr 的东西可以(通常/总是?)“不可变”,这就是const 的意思。【参考方案3】:

添加到@max66 答案:constexpr 只能替换一个*** const。它永远不能替换指向 const 或 const 引用的指针。所以,有时constexprconst 可以在同一个声明中使用。例如

const char* const s = "Hello";

可以替换为:

constexpr const char* s = "Hello";

【讨论】:

现在考虑const char* const s = getValueFromSomewhere();

以上是关于将 constexpr 添加到语言后是不是将变量声明为 const 多余?的主要内容,如果未能解决你的问题,请参考以下文章

关于constexpr

函数内的静态 constexpr 变量是不是有意义?

哪些值可以分配给 `constexpr` 引用?

Constexpr变量不是编译时间值吗?

如何声明 constexpr C 字符串?

C++constexpr和常量表达式