C++ 三元运算符调用复制构造函数而不是移动构造函数

C++ Ternary Operator Calls Copy Constructor Instead of Move Constructor

我在 Linux.

中使用 VS Code 通过 g++ 进行编译和调试

需要包含和使用:

#include <string>
#include <iostream>

using namespace std;

这是我的 class,它是可移动的:

class A {
public:
    A(const string& strA) : strA(strA) {}

    A(const A& a) : A(a.strA) {
    }

    A(A&& a) : A(a.strA) {
        a.strA = "";
    }

    string strA;
};

returns A 实例的示例函数:

A RetA() {
    A a("a");
    A b("bha");

    string ex;
    cin >> ex;
    a.strA += ex;

    return ex == "123" ? a : b;
}

这是简单的主要部分:

int main() {
    A a(RetA());

    return 0;
}

并且RetA函数中的返回值是复制的未移动。为什么?

另一方面,如果我们在 RetA 函数中使用“显式 if”而不是三元运算符:

A RetA() {
    A a("a");
    A b("bha");

    string ex;
    cin >> ex;
    a.strA += ex;

    if (ex == "123")
        return a;

    return b;
}

那就是移动了没有复制。这已经是预期的行为。但奇怪的是,移动操作不适用于三元运算符。应该是那样还是 VS Code 等的错误或其他问题?

return 语句中的“自动”移动是有限的:

来自Automatic move from local variables and parameters

If expression is a (possibly parenthesized) id-expression that names a variable whose type is either [..]

return ex == "123" ? a : b;并非如此。

然后正常的方式就完成了,ex == "123" ? a : b return一个左值,所以复制发生了。

你可能会

return std::move(ex == "123" ? a : b);

return ex == "123" ? std::move(a) : std::move(b);

有说明书move.

使用if 允许遵循上述规则自动移动

if (ex == "123")
    return a;
else
    return b;