[move] Move c-tor template

Hi, I am implementing custom smart pointer with move semantics and I am having problems with implementing move constructor with template param. In fact clone_ptr presented in docs suffers from that issue also. This code: class B {} class D: public B {} clone_ptr<D> makeD(); void main() { clone_ptr<B> b = makeD() // gives "error C2440: 'initializing' : cannot convert from 'clone_ptr<T>' to 'clone_ptr<T>'" } adding template <class U> clone_ptr(BOOST_RV_REF(clone_ptr<U>) p) //Move constructor : ptr(p.ptr) { p.ptr = 0; } to clone_ptr class does not help. Additional c-tor seems to be ignored. How to fix that? Cheers, Simon -- Szymon Gatner The Lordz Games Studio www.thelordzgamesstudio.com

On Fri, Mar 30, 2012 at 8:11 AM, Szymon Gatner
Hi,
I am implementing custom smart pointer with move semantics and I am having problems with implementing move constructor with template param. In fact clone_ptr presented in docs suffers from that issue also. This code:
class B {} class D: public B {}
clone_ptr<D> makeD();
void main() { clone_ptr<B> b = makeD() // gives "error C2440: 'initializing' : cannot convert from 'clone_ptr<T>' to 'clone_ptr<T>'" }
adding
template <class U> clone_ptr(BOOST_RV_REF(clone_ptr<U>) p) //Move constructor : ptr(p.ptr) { p.ptr = 0; }
to clone_ptr class does not help. Additional c-tor seems to be ignored. How to fix that?
Unfortunately, you can't catch rvalues of a move-emulation-enabled type in a deduced context as you've tried to above (in C++03). If you want some ideas on how to get something like this to work, search the Boost developer list under the messages subject "[boost] [move] new rvalue reference emulation". The easiest solution, though, is simply to split the construction into two steps: clone_ptr<D> d = makeD(); clone_ptr<B> b = boost::move(d); (This still requires the additional constructor you've given above!) I *think*, due to RVO, there shouldn't be any overhead with the above pair of statements compared with rolling everything into a single statement. If this doesn't fulfill your needs, I suggest reading through the thread given above in the Boost developer list. HTH, - Jeff

Unfortunately, you can't catch rvalues of a move-emulation-enabled type in a deduced context as you've tried to above (in C++03). If you want some ideas on how to get something like this to work, search the Boost developer list under the messages subject "[boost] [move] new rvalue reference emulation".
The easiest solution, though, is simply to split the construction into two steps:
clone_ptr<D> d = makeD(); clone_ptr<B> b = boost::move(d);
(This still requires the additional constructor you've given above!) I *think*, due to RVO, there shouldn't be any overhead with the above pair of statements compared with rolling everything into a single statement.
If this doesn't fulfill your needs, I suggest reading through the thread given above in the Boost developer list.
Thanks a lot for your answer, reading into the source you suggested now. It is a serious drawback of move emulation tho imho as pointer upcasting is rater basic (smart) pointer related stuff. Time to update a compiler I guess ;) Cheers! Simon
participants (2)
-
Jeffrey Lee Hellrung, Jr.
-
Szymon Gatner