简体   繁体   English

绑定可修改的右值引用到可修改的左值

[英]Binding modifiable rvalue reference to modifiable lvalue

I have 3 questions: 我有3个问题:

  1. Can I bind a lvalue directly to a rvalue reference? 我可以将左值直接绑定到右值参考吗?

  2. What happens to the object that being std::move() ? 作为std::move()的对象会发生什么?

  3. What's the difference between std::move and std::forward ? std :: move和std::forward之间有什么区别?

struct myStr{
    int m_i;
};

void foo(myStr&& rs) { }

myStr rValueGene()
{
    return myStr();
}

int main() 
{
    myStr mS= {1};
    foo(rValueGene()); //ok passing in modifiable rvalue to rvalue reference

    // To Question 1:
    //below initilize rvalue reference with modifiable lvalue, should be ok
    //but VS2010 gives a compile error: error C2440: 'initializing' : cannot convert from    'myStr' to 'myStr &&' 
    //Is this correct ?
    myStr&& rvalueRef = mS;

    //by using std::move it seems ok, is this the standard way of doing this 
    //to pass a lvalue to rvalue reference
    //myStr&& rvalueRef = std::move(mS);

    // To Question 2:    
    //also what happens to mS object after std::move ?
    //destroyed , undefined ?
}

1>Can I bind a lvalue directly to a rvalue reference ? 1>我可以将左值直接绑定到右值参考吗?

Not without an explicit cast (ie: std::move ). 不是没有显式的强制转换(即: std::move )。

2>What happens to the object that being std::move() ? 2> std :: move()对象会发生什么?

Nothing until it is actually moved. 没有什么,直到它实际上被移动。 All std::move does is return an r-value reference to what you gave it. 所有std::move都返回一个对你给它的r值引用。 The actual moving happens in the move constructor/assignment of the type in question. 实际移动发生在相关类型的移动构造函数/赋值中。

3>What's the difference between std::move and std::forward ? 3> std :: move和std :: forward有什么区别?

std::move is for moving; std::move用于移动; std::forward is for forwarding. std::forward用于转发。 That sounds glib, but that's the idea. 这听起来很滑稽,但这就是主意。 If you are intending for an object to be moved, then you use std::move . 如果您打算移动一个对象,那么您使用std::move If you are intending for an object to be forwarded, you use std::forward . 如果您打算转发对象,请使用std::forward

Forwarding uses specialized semantics that allow conversions between types of references, so that the reference natures are preserved between calls. 转发使用允许在引用类型之间进行转换的专用语义,以便在调用之间保留引用性质。 The specifics of all of this are very... technical. 所有这些的具体细节都非常......技术性。

std::move always returns a &&. std::move 总是返回一个&&。 If you give it an l-value reference, it returns an r-value reference. 如果给它一个l值引用,它将返回一个r值引用。 If you give it a value type, it returns an r-value reference to that value. 如果为其指定值类型,则返回对该值的r值引用。 And so forth. 等等。

std::forward does not always return a &&. std::forward 并不总是返回一个&&。 Syntactically, std::forward is just doing a static_cast<T&&> . 从语法上讲, std::forward就是在做一个static_cast<T&&> However, because of specialized syntax around casting to && types, this cast does not always return a &&. 但是,由于围绕转换为&&类型的专门语法,此强制转换并不总是返回&&。 Yes, that's weird, but it solves the forwarding problem, so nobody cares. 是的,这很奇怪,但它解决了转发问题,所以没人关心。 That's why it's contained in std::forward , rather than having to explicitly do the static_cast yourself. 这就是为什么它包含在std::forward ,而不是自己明确地执行static_cast

Question 1. Yes, the compiler is correct. 问题1.是的,编译器是正确的。

Question 2. Nothing happens. 问题2.没有任何反应。 std::move just casts things to rvalues. std::move只是将事物转换为rvalues。

If however you were to use std::move to pass mS (or myStr ) to foo , then that function might assume that it can "steal" the object and thus mS might end up in an unspecified state after the function call. 但是,如果您使用std::movemS (或myStr )传递给foo ,那么该函数可能会认为它可以“窃取”该对象,因此在函数调用之后mS可能最终处于未指定状态。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM