c++ - C++ 17中的静态constexpr和静态内联变量有什么区别?

标签 c++ c++17 constexpr

在 C++17 中,我们得到内联变量。

它们的用途之一是在类中定义常量字段。

那么这两个常量定义有什么区别:

class MyClass {
    static constexpr int myFirstVar = 10;
    static const inline int mySecondVar = 100;
};

当然 constexpr 使 myFirstVar 隐式内联。

这里有什么更好的选择,使用 constexprinline

注意:当你不需要 constness 时,inline 会更容易。使用 constexpr 你没有那个选择。

最佳答案

您不必在声明时为 mySecondVar 指定初始化程序。 constexpr 本身也不需要初始化器。

这意味着如果我们尝试像这样定义 myFirstVar:

class MyClass {
    static constexpr int myFirstVar;
};

int MyClass::myFirstVar = 1;

或者像这样:

#include <cstdlib>

class MyClass {
    static constexpr int myFirstVar = rand();
};

无论哪种方式,它都是不正确的。 constexpr 语义要求它并且有充分的理由。

inline 说明符方法允许我们在 header 本身中包含静态变量定义,而初始值设定项不是 constexpr;或者如果初始化程序相当复杂,它不必在类定义本身中。

所以这是 C++17 中一个完全有效的 header :

#include <cstdlib>

class MyClass {
    static const int mySecondVar;
};

inline const int MyClass::mySecondVar = rand();

该标准向我们保证,包含 header 的所有翻译单元都将看到相同的变量值,即使我们直到运行时才知道它是什么。

它主要是一个库编写器工具。假设您的库只是标题。那么在过去,如果您需要这样定义的静态常量,您有什么选择?

好吧,您可以在库中附带一个目标文件。它将从只包含常量定义的翻译单元编译。现在该库不再是仅 header 了。

或者您可以改用内联函数。内联变量效果可以通过以下方式实现:

class MyClass {
    static inline int mySecondVar();
};

inline int MyClass::mySecondVar() {
  static const int value = rand();
  return value;
}

但它隐藏在语法墙后面,并用函数调用运算符掩盖了本质上是常量的内容。

关于c++ - C++ 17中的静态constexpr和静态内联变量有什么区别?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45183324/

相关文章:

c++ - 在未使用 constexpr 函数的返回值的情况下,g++ 编译器是否将其视为常规函数?

c++ - 子线程发出一个被忽略的信号

c++ - 无法在列表 vector 中使用列表

c++ - 存储和调用具有未知参数的成员函数

c++ - 使用折叠表达式扩展带有索引的参数包

c++ - 从 C++14 模板特化中删除 constexpr?

c++ - G++ 和 STD 11 在 constexpr 方面存在问题

c++ - 类的重新定义

c# - 从文本框获取数据到数组

c++ - 类型安全的可变参数函数