C++定义构造函数使对象非POD。

问题描述 投票:0回答:1

如果我有一个简单的结构 Foo,这样定义,就是一个POD。

#include <iostream>
#include <type_traits>

struct Foo {
  int a;
  int b;
  bool c;
};

int main() {
  std::cout << (std::is_pod<Foo>::value ? "POD" : "NON POD") << '\n'; // Prints "POD"
}

现在想象一下,我想默认初始化成员,然后直接这样做,这结构就不再是POD了!

struct Foo {
  int a;
  int b;
  bool c = true;
};

这个结构就不再是一个POD了!即使有了这样的构造函数,Foo也失去了它的POD性..:

struct Foo {
  int a;
  int b;
  bool c;

  Foo() : a(0), b(0), c(false) {}
};

Foo已经失去了它的POD性... ...

现在,棘手的部分开始了。想象一下,我想添加一个构造函数,在结构体上取一个 "POD"。a:

struct Foo {
  int a;
  int b;
  bool c;

  Foo(int a) : a(a), b(0), c(false) {}
};

现在Foo绝对不是一个POD。但是,如果添加一个默认的构造函数,Foo现在是一个POD了。

struct Foo {
  int a;
  int b;
  bool c;

  Foo() = default;
  Foo(int a) : a(a), b(0), c(false) {}
};

Foo就变成了一个POD!

所以正如你所看到的,即使我只是想使用一个默认值,就像第二个例子一样,我失去了POD性,但只要我定义一个显式的默认构造函数,我就可以重新获得它。

所以问题是:我们是否应该总是添加一个默认构造函数,这样我们就可以从类的POD性中获益,提高性能?如果因为我想默认初始化一些成员而损失性能,那就太糟糕了......

换句话说,像第二个例子那样定义默认值会使结构变得非POD和非琐碎,从性能上来说是很糟糕的,那么我怎样才能默认初始化值并保持结构的琐碎呢?一个简单的解决方案就是定义一个 initFoo 函数,返回一个默认初始化的Foo,比如说。

Foo initFoo() {
  Foo foo;
  foo.a = 0;
  foo.b = 1;
  foo.c = true;
  return foo;
}

但这不是很C++,但无论如何,这样做对吗?

c++ default-constructor
1个回答
1
投票

我们是否应该总是添加一个默认的构造函数,这样我们就可以从类的POD性中获益。

如果你想让一个类成为POD,那么除了其他要求外,它必须是可默认构造的。

实现这个要求的一种方法是不声明任何构造函数,也不声明默认成员初始化器。另一种方法是将默认构造函数定义为默认。如果你希望类有任何非默认构造函数,后一种方法是唯一的方法。

就POD性而言,你选择哪种方法并不重要。


但无论如何,这样做是正确的吗?

你的 initFoo 是一种正确的返回方式 Foo 与特定的值。就个人而言,我不认为局部变量有价值,而会这样做。

return {
    0,
    1,
    true,
};

不幸的是,我们失去了初始化器中的成员名称, 至少在C++20之前,我们可以写:

return {
    .a = 0,
    .b = 1,
    .c = true,
};
© www.soinside.com 2019 - 2024. All rights reserved.