Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to forward unique_ptr with tuple?

Imagine a function expecting rvalue reference to std::unique_ptr.

void foo(std::unique_ptr<int>&& a);

In my real world example there is more than one argument, so I decided to forward arguments to it using std::tuple<T&&> of rvalue references - so std::forward_as_tuple:

void forward_to_foo(std::tuple<std::unique_ptr<int>&&>&& t);
int main() {
   forward_to_foo(std::forward_as_tuple(std::make_unique<int>(8)));
}

As for now everything is ok.

Problem occurred when I wanted to "unpack" this tuple

void forward_to_foo(std::tuple<std::unique_ptr<int>&&>&& t)
{
   foo(std::get<0>(t));
}

I got this error on gcc4.9 with c++14:

error: cannot bind 'std::unique_ptr<int>' lvalue to 'std::unique_ptr<int>&&'
    foo(std::get<0>(t));

My question: what is the problem here? Why std::get<I>(t) from tuple of rvalue references returns lvalue?

like image 505
PiotrNycz Avatar asked Mar 16 '15 15:03

PiotrNycz


1 Answers

what is the problem here?

You need std::move to move from an lvalue expression:

foo(std::move(std::get<0>(t)));

Why std::get<I>(t) from tuple of rvalue references returns lvalue?

Because it returns an lvalue reference to an element of the tuple. In general, the result of a function returning an lvalue reference is an lvalue, since it denotes an existing object not a temporary.

like image 93
Mike Seymour Avatar answered Nov 11 '22 22:11

Mike Seymour