rvalue references and default constructors

  • Thread starter Paul Brettschneider
  • Start date
P

Paul Brettschneider

Hello,

C++0x introduces the concept of rvalue-references (described for example
here: http://www.artima.com/cppsource/rvalue.html) and, if I got this
right, an rvalue-reference is an invitation to mutilate the referenced
object since it is a temporary which will not be used anymore. Which
enables us to implement (amongst other things) move semantics.

But, inside a function which gets an rvalue-reference it is treated like a
normal reference, which makes sense since you don't want your object
destroyed after accessing it once.

std::move() will turn a normal (lvalue-)reference into an rvalue-reference.
Therefore the idiomatic rvalue-copy-constructor and
rvalue-assignment-operator will look like this:

class Test : public Base {
Object a;
public:
Test(Test &&t)
: Base(std::move(t))
, a(std::move(t.a))
{ };
Test &operator=(Test &&t)
{
Base::eek:perator=(std::move(t));
a = std::move(t.a);
return *this;
}
};

So my question is: will the rvalue-copy-constructor and the
rvalue-copy-operator be automaticall generated or will we have to write it
on our own?

Thanks!
 
E

Erik Wikström

Hello,

C++0x introduces the concept of rvalue-references (described for example
here: http://www.artima.com/cppsource/rvalue.html) and, if I got this
right, an rvalue-reference is an invitation to mutilate the referenced
object since it is a temporary which will not be used anymore. Which
enables us to implement (amongst other things) move semantics.

But, inside a function which gets an rvalue-reference it is treated like a
normal reference, which makes sense since you don't want your object
destroyed after accessing it once.

std::move() will turn a normal (lvalue-)reference into an rvalue-reference.
Therefore the idiomatic rvalue-copy-constructor and
rvalue-assignment-operator will look like this:

class Test : public Base {
Object a;
public:
Test(Test &&t)
: Base(std::move(t))
, a(std::move(t.a))
{ };
Test &operator=(Test &&t)
{
Base::eek:perator=(std::move(t));
a = std::move(t.a);
return *this;
}
};

So my question is: will the rvalue-copy-constructor and the
rvalue-copy-operator be automaticall generated or will we have to write it
on our own?

Doing a quick search of the latest draft I found nothing about
implicitly declared rvalue constructors.
 
P

Paul Brettschneider

Erik said:
Doing a quick search of the latest draft I found nothing about
implicitly declared rvalue constructors.

Me neither. And it makes me wonder, since given that this feature looks so
obvious at a first glance, one would expect the standard to lose a word or
two on why this will or will not be implemented, isn't it?
 
F

Frank Bergemann

So my question is: will the rvalue-copy-constructor and the
rvalue-copy-operator be automaticall generated or will we have to write it
on our own?

Using gcc-4.3.0 it silenty(!) invokes the Test::eek:perator=(Test const&
t) for

Test a;
Test b = std::move(a);
Test c = std::moved(T());

- if i disable the Test::eek:perator=(Test&& t) in source file.
(But uses Test::eek:perator=(Test&& t) if it is availabled.)

Though using std::move() might be considered to be an explicit request
for rvalue reference argumented function.


Moreover:
One MUST use std::move(t) for explicit invocation of
Base::eek:perator=(Base&& rhs) in Test::eek:perator=(Test&& t)

Test &operator=(Test &&t)
{
Base::eek:perator=(std::move(t)); // HERE
a = std::move(t);
return *this;
}

Otherwise it calls Base::eek:perator=(Base const& rhs) silently again.

Using member functions with rvalue reference arguments seems just to
be a "fits better" for the compiler.
Member functions with rvalue reference type arguments attract for
applying actual rvalue references to some overloaded member function
set - as forced by std::move().

Worse in my view is, that inside those functions itself- which have
rvalue reference arguments - those types are treated like lvalue
references again (see the need for explicit std::move(t) in
Test::eek:perator=(Test&& t).
I guess the reason is that it MIGHT be given some lvalue reference as
well - for invocation
(For test you can also do the other way around: provide rvalue
reference member functions and drop/disable the old "Test const& t"
images.)
So it falls back to that restriction level - unless you explicitly
recover rvalue reference conditions (using std::move() again).
This is feels like sapping type-safety.
Or let me say: if i declare a rvalue reference argument for my member
function i would like to keep treating it as rvalue reference inside
that function.

rgds!

Frank
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,744
Messages
2,569,484
Members
44,903
Latest member
orderPeak8CBDGummies

Latest Threads

Top