当前位置: 首页 > 知识库问答 >
问题:

只有一个构造函数被调用[重复]

柯升
2023-03-14

我试图理解右值引用。这是我迄今为止编写的代码:

class A {
public:
    A(const char* str) {
        std::cout << str;
    }

    A(A&& other) {
        std::cout << "other";
    }
};

int main() {
    A m(A(A(A("hello"))));
}

输出只有< code >“hello”,这让我很困惑。

由于 A(“hello”) 是传递给第二个构造函数的临时对象,因此代码输出就好像只调用第一个构造函数一样。

我猜这要么是编译器优化,要么我错过了关于构造函数和右值的一些细节。

共有2个答案

蒋奕
2023-03-14

是的,这是一个编译器/语言(见后面)优化。

正如这里可以看到的,这将输出:

hello

将编译器选项中的标准从-std=c 2a更改为-std=c 14仍然只会给您hello,但除了标准更改之外,如果您还添加:-fno-elide-构造函数到选项中,您应该会看到您所希望的。

但是,如果您指定C 17或C 2a作为标准,此选项将不再有效,因为在某些情况下此省略已成为强制性的,因为这些标准,您的情况就是其中之一。

堵宪
2023-03-14

你观察到的也被称为复制省略,更准确地说:

在以下情况下,编译器需要省略类对象的复制和移动构造,即使 copy/move 构造函数和析构函数具有可观察到的副作用。对象被直接构造到存储中,否则它们将被复制/移动到存储中。复制/移动构造函数不必存在或可访问:

(...)

  • 在对象初始化中,当初始值设定项表达式是与变量类型相同的类类型(忽略cv限定)的prvalue时:

T x=T(T(f());//只有一次调用T的默认构造函数,以初始化x

这正是你的情况。

请注意,从C 17开始,优化是强制性的。它对于C 11是可选的,但您的编译器似乎无论如何都应用了它。

 类似资料:
  • 我的问题是关于OOP(C)中的构造函数。当我在一个类中将默认构造函数定义为private,并且在main中将该类的一个对象初始化为default时,就会出现默认构造函数不可访问的错误。这很好。但我也在Public部分中使用默认参数构造函数,当我再次在main中初始化对象时,就会出现对函数重载的不明确调用。所以我的问题是,如果不能从main访问私有构造函数,那么编译器应该调用公共部分中的构造函数,这

  • 所以我有这个错误,使用robolectric。

  • 我有一张JTABLE。为JTable中的一列分配了一个显示扩展JComboBox的扩展TableCellEditor。 挑战: 设计JComboBoxes使任何选择相对于其他框都是唯一的?也就是说,如果从第一行的组合框中选择了“a”,则会自动将其从其他组合框的列表中删除。 将新房间添加到表中时,它包含的组合框应自动填充到第一个可用列表项。 问题是:我的组合框工作得很好。我可以随意挑选物品。我甚至在

  • 我需要避免重复的代码与这些构造函数,所以我想知道是否有一种方法来实例化这些变量只有一个?我看到了很多关于链接的帖子,但我还没有让它正常工作。

  • 问题内容: 我在一个Activity中有一个IntentService,当我尝试调用该服务时,它将引发此错误,我发现这很奇怪,因为如果我声明了空的构造函数。 错误: AndroidManifest.xml 活动: 问题答案: 你是一个内部阶级。如果要将其保留在内部,请将其更改为static: 您可能需要阅读不同类型的嵌套类。google的第一个链接:http : //docs.oracle.com

  • 问题内容: 构造函数何时被调用? 创建对象之前。 在对象创建期间。 创建对象之后。 问题答案: 分配对象内存,初始化具有初始值的字段变量,然后调用构造函数,但是其代码在对象超类的构造函数代码之后执行。