4
#include <iostream>

class Foo { };

Foo createFoo() { return Foo(); }

void bar(Foo &&) { std::cout << "in bar(Foo &&)\n"; }

void bar(Foo const &) { std::cout << "in bar(Foo const &)\n"; }

void baz(Foo &&f) {
    std::cout << "in baz, ";
    bar(f);
    // bar(std::move(f));
}

int main()
{
    baz(createFoo());
    return 0;
}

我的预期输出是:in baz, in bar(Foo &&),但我得到:in baz, in bar(Foo const &)。如果我将调用切换到bar(参见评论),我会得到预期的输出,但这对我来说似乎是错误的。bar(Foo &&)如果没有我将 a 转换Foo&&为 a ,编译器是否无法调用Foo&&

提前致谢!

4

2 回答 2

13

里面baz(Foo&& f)f是一个左值。因此,要将其bar作为右值引用传递,您必须将其转换为右值。您可以使用static_cast<Foo&&>(f)或执行此操作std::move(f)

这是为了避免在同一个函数中多次意外移动内容,例如多次调用bar(f)inside baz

于 2012-05-15T15:52:17.437 回答
4

简而言之,规则是命名的右值引用是一个左值。这是为了防止自动移出稍后需要使用的命名变量。相反,未命名的临时对象永远不能再次使用,因此可以自动移出。

我发现这个系列http://cpp-next.com/archive/2009/08/want-speed-pass-by-value/非常有用,尽管它有点旧。

于 2012-05-15T15:56:25.707 回答