【问题标题】:Why C++ does allow in-class definition?为什么 C++ 允许类内定义?
【发布时间】:2021-11-25 17:34:17
【问题描述】:

课堂定义是否违反了 ODR 规则?

Bjarne Stroustrup 的 explanation 指出:

一个类通常在头文件中声明,头文件通常包含在许多翻译单元中。但是,为了避免复杂的链接器规则,C++ 要求每个对象都有唯一的定义。如果 C++ 允许在类内定义需要作为对象存储在内存中的实体,则该规则将被打破。

class foo 
{
    float f = 1.1f;
    int i = 1;
    string s = "foo";
    long long ll = 44ll;
};

这是成员的实际定义吗?这是否违反 ODR 规则?如果不是,与通过构造函数进行初始化相比,这样做有什么优势?

【问题讨论】:

  • 方便简洁。不。不。不。方便和简洁。
  • “与通过构造函数进行初始化相比,这样做有什么优势” 您刚刚证明了 - 不必编写那些构造函数。此外,如果有多个构造函数,您只需编写一次此初始化。

标签: c++ in-class-initialization


【解决方案1】:

课堂定义是否违反了 ODR 规则?

你展示的不是“定义”。它是默认的成员初始化器。如果在初始化类的实例时未为非静态数据成员提供默认初始化程序,则将使用此默认初始化程序。

该示例不违反 ODR。

从技术上讲,该标准并未提及如何定义非静态数据成员。然而,它们似乎并没有被排除在“odr-used”之外,这可能是标准措辞中的一个缺陷。定义的需要并不真正适用于子对象。

【讨论】:

    【解决方案2】:

    在类中初始化帮助我们设置成员的默认状态(这反过来又让我们设置了整个对象的默认状态)。例如,如果您希望给定类的任何对象都应该具有默认值(状态),那么您应该使用类内初始化。

    使用类内初始化还有一个原因。如果您不为内置类型提供类内初始化器,那么它们将具有垃圾值。也就是说,我们不能说该数据成员的值,这不是我们想要的。

    这就是为什么总是建议您初始化非静态内置类型数据成员的原因。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-09-16
      • 2014-04-07
      • 1970-01-01
      • 2012-09-02
      • 1970-01-01
      • 1970-01-01
      • 2012-04-22
      • 2023-04-07
      相关资源
      最近更新 更多