Как работает параметр rvalue?

Так что я просто удивился, обнаружив, что в этом коде:

void AddLayer( shared_Layer_ptr && pNewLayer_p ){

m_layers.push_back( pNewLayer_p ); // *
}

Вызываемый push_back является «& парам «а не то»&& param «версия. m_layers является std :: vector.
Поскольку pNewLayer_p является «&&»Я думал, что это чертово значение … Единственный способ, которым мне удается получить push_back («&& Вызывается param «) с помощью std :: move:

m_layers.push_back( std::move(pNewLayer_p) );

Мне кажется излишним, так как pNewLayer_p уже «&&».. Я уверен, что что-то упустил, что это?

4

Решение

pNewLayer_p является ссылкой на rvalue, но сама по себе не является rvalue — в основном потому, что у нее есть имя. Значения определяются в Стандарте следующим образом:

(3.10 / 1) rvalue (так называемый, исторически, потому что rvalue мог появиться в правой части выражения присваивания) является xvalue, временным объектом (12.2) или его подобъектом, или значением, которое не связано с объект.

Другими словами, rvalues ​​- это литералы, временные и другие неназванные объекты (такие как xvalues, то есть значения, которые только что были возвращены функцией, но еще никому не были назначены).

Rvalue ссылка pNewLayer_p в вашем коде есть именованный объект, поэтому он сам является lvalue. применение std::move для него, который формально является функцией, превращает его (формально) во что-то, возвращаемое из функции, то есть в xvalue, которое является значением, которое вы можете передать в версию перемещения push_back, Это то, что std::move существует для.

(Примечание: вышеизложенное предполагает, что shared_Layer_ptr это тип, а не параметр шаблона. Если это параметр шаблона, shared_Layer_ptr && будет так называемой универсальной ссылкой, то есть это может быть ссылка lvalue или ссылка rvalue в зависимости от того, как создается экземпляр шаблона. В этом случае, std::forward будет подходящей функцией для использования вместо std::move.)

2

Другие решения

Подумай, что случится, если он начнет двигаться pNewLayer,

void AddLayer( shared_Layer_ptr && pNewLayer_p ){
m_layers.push_back( pNewLayer_p );
// what if pNewLayer_p is already moved
another_m_layers.push_back( pNewLayer_p );
}

Поэтому вы должны использовать std::move в явном виде:

void AddLayer( shared_Layer_ptr && pNewLayer_p ){
m_layers.push_back( pNewLayer_p );
another_m_layers.push_back( std::move(pNewLayer_p) );
}

Если ссылка на rvalue может появляться в функции только один раз, это определенно удалит некоторую мощность из C ++.

2

По вопросам рекламы [email protected]