C++17 复制省略规则并隐式移动

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

有下面一段代码

#include <iostream>

class A {
public:
    A() {}

    // Explicit move constructor
     A(A&&) noexcept {
        std::cout << "move ctor" << std::endl;
    }

    // Copy constructor is deleted
    A(const A&) = delete;

    char x;
};
A a;
A foo() {
    A a;
    return a;  // Return by value, let the compiler apply move semantics
}
A bar() {
    
    return a;  // Return by value, let the compiler apply move semantics
}
int main() {
    A a = foo();  // Explicit move of the returned object
    A a2 = bar();
}

使用以下参数进行编译 --std=c++17 -fno-elide-constructors 示例 在 foo 内部,如果 x 符合移动条件,则根据标准禁用复制省略,因此表达式 x 是右值。 否则,它是左值。

基于此调用移动构造函数。

对于 bar,返回值是具有静态存储的 a。 为此,不会隐式调用移动构造函数。需要明确使用移动。我的问题是为什么这种差异基于变量 a 的存储?

c++ c++17 move return-value-optimization
1个回答
0
投票

我的问题是为什么这种差异基于变量 a 的存储?

因为如果在函数中简单地写

return a;
意味着
a
的状态将在下次使用时丢失,那将是致命的。想象一下你有

std::vector<int> x;
std::vector<int> f() { return x; }

然后希望每次调用

x
f
都会变空?

自动移动具有自动存储持续时间的局部变量有意义的唯一原因是我们知道一旦函数退出,它们就不能再使用了。

© www.soinside.com 2019 - 2024. All rights reserved.