Компилятор выполняет оптимизацию возвращаемого значения в случае возврата переменной-члена?
Учитывая следующий код
class foo
{
private:
boost::shared_ptr <std::deque<foo> > m_ptr;
public:
foo();
boost::shared_ptr <std::deque<foo> > get_my_ptr()
{
return m_ptr;
}
};
И когда мы позвоним get_my_ptr()
функционировать так
boost::shared_ptr <std::deque<foo> > ptr = get_my_ptr()
Вызывает ли компилятор конструктор копирования для создания объекта ptr или он может выполнять nrvo? И какая разница мы называем это так
const boost::shared_ptr <std::deque<foo> >& ptr = get_my_ptr()
2 ответа
При использовании NRVO компилятору разрешается опускать конструкции копирования и перемещения, если выражением оператора возврата является имя локального энергонезависимого объекта с автоматической продолжительностью хранения, который не является параметром функции. Этот локальный объект создается непосредственно в хранилище, куда в противном случае было бы скопировано возвращаемое значение функции. Эти условия не выполняются для переменных-членов. Это возможно только в том случае, если вы создали локальную копию участника:
boost::shared_ptr<std::deque<foo>> get_my_ptr()
{
auto p = m_ptr;
return p;
}
В вашем примере будет вызван экземпляр ctor, который увеличит счетчик ссылок общего указателя. То же самое произойдет, если вы привяжете возвращенный объект к константной ссылке.
Компиляция не должна выполнять RVO, когда возвращается переменная-член. Если это так, объект останется с недопустимым членом.