Topic: Add .emplace() method to std::unique_ptr and
Author: antanubis@gmail.com
Date: Mon, 30 Oct 2017 09:01:25 -0700 (PDT)
Raw View
------=_Part_6783_1151948913.1509379285772
Content-Type: multipart/alternative;
boundary="----=_Part_6784_322329998.1509379285772"
------=_Part_6784_322329998.1509379285772
Content-Type: text/plain; charset="UTF-8"
I've found really helpful in my own smart pointer classes to have something
like .create(Args &&..args) method that creates an object for an owning
shared pointer without the necessity for repeating the type in the make_*
non-member function.
It's a shame that standard smart pointers don't have such method, so in
order to create a value you always need to repeat the type name, while it
is contained in the pointer type itself.
After that I realized, that std::optional<> has such method named
..emplace() together with a free function make_optional<>. In some way
std::optional<> is a lot like "in-place std::unique_ptr<>" with
deep-copying by default.
So I thought that proposing a member function "ptr.emplace(Args&&... args)"
for both std::unique_ptr and std::shared_ptr will be a really good idea, it
will also fit well with std::optional. The naive (but working)
implementation would be just:
void(?) unique_ptr<T>::emplace(Args &&... args) { *this =
make_unique<T>(std::forward<Args>(args)...); }
void(?) shared_ptr<T>::emplace(Args &&... args) { *this =
make_shared<T>(std::forward<Args>(args)...); }
What do you think? Are there reasons not to add such methods? Or was this
discussed / proposed already?
Vasilii Babich.
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/58eb77f6-2c2d-4ec1-85f8-08dcfe25a23e%40isocpp.org.
------=_Part_6784_322329998.1509379285772
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr"><div>I've found really helpful in my own smart pointer=
classes to have something like .create(Args &&..args) method that =
creates an object for an owning shared pointer without the necessity for re=
peating the type in the make_* non-member function.</div><div><br></div><di=
v>It's a shame that standard smart pointers don't have such method,=
so in order to create a value you always need to repeat the type name, whi=
le it is contained in the pointer type itself.</div><div><br></div><div>Aft=
er that I realized, that std::optional<> has such method named .empla=
ce() together with a free function make_optional<>. In some way std::=
optional<> is a lot like "in-place std::unique_ptr<>"=
with deep-copying by default.</div><div><br></div><div>So I thought that p=
roposing a member function "ptr.emplace(Args&&... args)" =
for both std::unique_ptr and std::shared_ptr will be a really good idea, it=
will also fit well with std::optional. The naive (but working) implementat=
ion would be just:</div><div><br></div><div>void(?) unique_ptr<T>::em=
place(Args &&... args) { *this =3D make_unique<T>(std::forwar=
d<Args>(args)...); }</div><div>void(?) shared_ptr<T>::emplace(A=
rgs &&... args) { *this =3D make_shared<T>(std::forward<Ar=
gs>(args)...); }</div><div><br></div><div>What do you think? Are there r=
easons not to add such methods? Or was this discussed / proposed already?</=
div><div><br></div><div>Vasilii Babich.</div></div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/58eb77f6-2c2d-4ec1-85f8-08dcfe25a23e%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/58eb77f6-2c2d-4ec1-85f8-08dcfe25a23e=
%40isocpp.org</a>.<br />
------=_Part_6784_322329998.1509379285772--
------=_Part_6783_1151948913.1509379285772--
.
Author: antanubis@gmail.com
Date: Mon, 30 Oct 2017 09:05:15 -0700 (PDT)
Raw View
------=_Part_6589_877696603.1509379515759
Content-Type: multipart/alternative;
boundary="----=_Part_6590_1388151577.1509379515759"
------=_Part_6590_1388151577.1509379515759
Content-Type: text/plain; charset="UTF-8"
Perhaps being a nice substitution for "= make_...<T>(...)" the return type
should be the reference to smart pointer and the return value should be
*this.
On Monday, October 30, 2017 at 8:01:25 PM UTC+4, anta...@gmail.com wrote:
>
> I've found really helpful in my own smart pointer classes to have
> something like .create(Args &&..args) method that creates an object for an
> owning shared pointer without the necessity for repeating the type in the
> make_* non-member function.
>
> It's a shame that standard smart pointers don't have such method, so in
> order to create a value you always need to repeat the type name, while it
> is contained in the pointer type itself.
>
> After that I realized, that std::optional<> has such method named
> .emplace() together with a free function make_optional<>. In some way
> std::optional<> is a lot like "in-place std::unique_ptr<>" with
> deep-copying by default.
>
> So I thought that proposing a member function "ptr.emplace(Args&&...
> args)" for both std::unique_ptr and std::shared_ptr will be a really good
> idea, it will also fit well with std::optional. The naive (but working)
> implementation would be just:
>
> void(?) unique_ptr<T>::emplace(Args &&... args) { *this =
> make_unique<T>(std::forward<Args>(args)...); }
> void(?) shared_ptr<T>::emplace(Args &&... args) { *this =
> make_shared<T>(std::forward<Args>(args)...); }
>
> What do you think? Are there reasons not to add such methods? Or was this
> discussed / proposed already?
>
> Vasilii Babich.
>
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/db8aed18-d3b3-4df6-8e15-15f8c50e4bed%40isocpp.org.
------=_Part_6590_1388151577.1509379515759
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">Perhaps being a nice substitution for "=3D make_...&l=
t;T>(...)" the return type should be the reference to smart pointer=
and the return value should be *this.<br><br>On Monday, October 30, 2017 a=
t 8:01:25 PM UTC+4, anta...@gmail.com wrote:<blockquote class=3D"gmail_quot=
e" style=3D"margin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;paddin=
g-left: 1ex;"><div dir=3D"ltr"><div>I've found really helpful in my own=
smart pointer classes to have something like .create(Args &&..args=
) method that creates an object for an owning shared pointer without the ne=
cessity for repeating the type in the make_* non-member function.</div><div=
><br></div><div>It's a shame that standard smart pointers don't hav=
e such method, so in order to create a value you always need to repeat the =
type name, while it is contained in the pointer type itself.</div><div><br>=
</div><div>After that I realized, that std::optional<> has such metho=
d named .emplace() together with a free function make_optional<>. In =
some way std::optional<> is a lot like "in-place std::unique_ptr=
<>" with deep-copying by default.</div><div><br></div><div>So I =
thought that proposing a member function "ptr.emplace(Args&&..=
.. args)" for both std::unique_ptr and std::shared_ptr will be a really=
good idea, it will also fit well with std::optional. The naive (but workin=
g) implementation would be just:</div><div><br></div><div>void(?) unique_pt=
r<T>::emplace(Args &&... args) { *this =3D make_unique<T&g=
t;(std::forward<<wbr>Args>(args)...); }</div><div>void(?) shared_ptr&=
lt;T>::emplace(Args &&... args) { *this =3D make_shared<T>=
(std::forward<<wbr>Args>(args)...); }</div><div><br></div><div>What d=
o you think? Are there reasons not to add such methods? Or was this discuss=
ed / proposed already?</div><div><br></div><div>Vasilii Babich.</div></div>=
</blockquote></div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/db8aed18-d3b3-4df6-8e15-15f8c50e4bed%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/db8aed18-d3b3-4df6-8e15-15f8c50e4bed=
%40isocpp.org</a>.<br />
------=_Part_6590_1388151577.1509379515759--
------=_Part_6589_877696603.1509379515759--
.
Author: Ville Voutilainen <ville.voutilainen@gmail.com>
Date: Mon, 30 Oct 2017 18:06:45 +0200
Raw View
On 30 October 2017 at 18:05, <antanubis@gmail.com> wrote:
> Perhaps being a nice substitution for "= make_...<T>(...)" the return type
> should be the reference to smart pointer and the return value should be
> *this.
The idea looks reasonable enough to me that I would recommend writing
a proposal for it.
>
> On Monday, October 30, 2017 at 8:01:25 PM UTC+4, anta...@gmail.com wrote:
>>
>> I've found really helpful in my own smart pointer classes to have
>> something like .create(Args &&..args) method that creates an object for an
>> owning shared pointer without the necessity for repeating the type in the
>> make_* non-member function.
>>
>> It's a shame that standard smart pointers don't have such method, so in
>> order to create a value you always need to repeat the type name, while it is
>> contained in the pointer type itself.
>>
>> After that I realized, that std::optional<> has such method named
>> .emplace() together with a free function make_optional<>. In some way
>> std::optional<> is a lot like "in-place std::unique_ptr<>" with deep-copying
>> by default.
>>
>> So I thought that proposing a member function "ptr.emplace(Args&&...
>> args)" for both std::unique_ptr and std::shared_ptr will be a really good
>> idea, it will also fit well with std::optional. The naive (but working)
>> implementation would be just:
>>
>> void(?) unique_ptr<T>::emplace(Args &&... args) { *this =
>> make_unique<T>(std::forward<Args>(args)...); }
>> void(?) shared_ptr<T>::emplace(Args &&... args) { *this =
>> make_shared<T>(std::forward<Args>(args)...); }
>>
>> What do you think? Are there reasons not to add such methods? Or was this
>> discussed / proposed already?
>>
>> Vasilii Babich.
>
> --
> You received this message because you are subscribed to the Google Groups
> "ISO C++ Standard - Future Proposals" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to std-proposals+unsubscribe@isocpp.org.
> To post to this group, send email to std-proposals@isocpp.org.
> To view this discussion on the web visit
> https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/db8aed18-d3b3-4df6-8e15-15f8c50e4bed%40isocpp.org.
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/CAFk2RUaq1T6tMwAwsdkyorNM8gt550mYRwWkWGWa6gX4a%3D7koQ%40mail.gmail.com.
.
Author: Nevin Liber <nevin@eviloverlord.com>
Date: Mon, 30 Oct 2017 11:37:53 -0500
Raw View
--089e082577e0fcdee3055cc6447c
Content-Type: text/plain; charset="UTF-8"
On Mon, Oct 30, 2017 at 11:05 AM, <antanubis@gmail.com> wrote:
> void(?) unique_ptr<T>::emplace(Args &&... args) { *this =
>> make_unique<T>(std::forward<Args>(args)...); }
>> void(?) shared_ptr<T>::emplace(Args &&... args) { *this =
>> make_shared<T>(std::forward<Args>(args)...); }
>>
>
Thoughts:
- Neither shared_ptr nor unique_ptr store an allocator, so
shared_ptr::emplace and unique_ptr::emplace are being tied to a particular
allocation scheme. This makes it harder when people refactor code to use
other allocation schemes.
- unique_ptr has a deleter, which may not go along with emplace calling
"new". Will this function still exist if default_delete<T> isn't being
used?
- Unless you templatize it, emplace will not work for polymorphic types,
which IMO is one of the major use cases for unique_ptr (and a less major
one for shared_ptr).
Note: I'm not saying these are reasons I would vote against such a
proposal; rather, these are things which need to be discussed in the
proposal.
--
Nevin ":-)" Liber <mailto:nevin@eviloverlord.com> +1-847-691-1404
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/CAGg_6%2BMhHrsgMcAsqr_BiQu584PzypU%2BGMaRsPuo8XQ7V4RdoA%40mail.gmail.com.
--089e082577e0fcdee3055cc6447c
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">On Mon, Oct 30, 2017 at 11:05 AM, <span dir=3D"ltr"><<=
a href=3D"mailto:antanubis@gmail.com" target=3D"_blank">antanubis@gmail.com=
</a>></span> wrote:<br><div class=3D"gmail_extra"><div class=3D"gmail_qu=
ote"><blockquote class=3D"gmail_quote" style=3D"margin:0 0 0 .8ex;border-le=
ft:1px #ccc solid;padding-left:1ex"><div dir=3D"ltr"><span class=3D""><bloc=
kquote class=3D"gmail_quote" style=3D"margin:0;margin-left:0.8ex;border-lef=
t:1px #ccc solid;padding-left:1ex"><div dir=3D"ltr"><div>void(?) unique_ptr=
<T>::emplace(Args &&... args) { *this =3D make_unique<T>=
;(std::forward<Ar<wbr>gs>(args)...); }</div><div>void(?) shared_ptr&l=
t;T>::emplace(Args &&... args) { *this =3D make_shared<T>(=
std::forward<Ar<wbr>gs>(args)...); }</div></div></blockquote></span><=
/div></blockquote><div><br></div><div>Thoughts:</div><div><ul><li>Neither s=
hared_ptr nor unique_ptr store an allocator, so shared_ptr::emplace and uni=
que_ptr::emplace are being tied to a particular allocation scheme.=C2=A0 Th=
is makes it harder when people refactor code to use other allocation scheme=
s.</li><li>unique_ptr has a deleter, which may not go along with emplace ca=
lling "new".=C2=A0 Will this function still exist if default_dele=
te<T> isn't being used?<br></li><li>Unless you templatize it, emp=
lace will not work for polymorphic types, which IMO is one of the major use=
cases for unique_ptr (and a less major one for shared_ptr).</li></ul><div>=
Note: =C2=A0I'm not saying these are reasons I would vote against such =
a proposal; rather, these are things which need to be discussed in the prop=
osal.</div></div></div>-- <br><div class=3D"gmail_signature" data-smartmail=
=3D"gmail_signature"><div dir=3D"ltr"><div><div dir=3D"ltr"><div>=C2=A0Nevi=
n ":-)" Liber=C2=A0 <mailto:<a href=3D"mailto:nevin@eviloverlo=
rd.com" target=3D"_blank">nevin@eviloverlord.com</a>> =C2=A0+1-847-691-1=
404</div></div></div></div></div>
</div></div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/CAGg_6%2BMhHrsgMcAsqr_BiQu584PzypU%2B=
GMaRsPuo8XQ7V4RdoA%40mail.gmail.com?utm_medium=3Demail&utm_source=3Dfooter"=
>https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/CAGg_6%2BMhHr=
sgMcAsqr_BiQu584PzypU%2BGMaRsPuo8XQ7V4RdoA%40mail.gmail.com</a>.<br />
--089e082577e0fcdee3055cc6447c--
.
Author: antanubis@gmail.com
Date: Mon, 30 Oct 2017 11:32:41 -0700 (PDT)
Raw View
------=_Part_7162_1126213429.1509388361835
Content-Type: multipart/alternative;
boundary="----=_Part_7163_1995014264.1509388361836"
------=_Part_7163_1995014264.1509388361836
Content-Type: text/plain; charset="UTF-8"
The first approach looks like this (attached).
1. Should I post it as a new topic or continue here?
2. Should I upload it to my hosting (or some preferred one) and post a link
or attaching the file is fine?
Thanks for your time,
Vasilii Babich.
On Monday, October 30, 2017 at 8:38:37 PM UTC+4, Nevin ":-)" Liber wrote:
>
> On Mon, Oct 30, 2017 at 11:05 AM, <anta...@gmail.com <javascript:>> wrote:
>
>> void(?) unique_ptr<T>::emplace(Args &&... args) { *this =
>>> make_unique<T>(std::forward<Args>(args)...); }
>>> void(?) shared_ptr<T>::emplace(Args &&... args) { *this =
>>> make_shared<T>(std::forward<Args>(args)...); }
>>>
>>
> Thoughts:
>
> - Neither shared_ptr nor unique_ptr store an allocator, so
> shared_ptr::emplace and unique_ptr::emplace are being tied to a particular
> allocation scheme. This makes it harder when people refactor code to use
> other allocation schemes.
> - unique_ptr has a deleter, which may not go along with emplace
> calling "new". Will this function still exist if default_delete<T> isn't
> being used?
> - Unless you templatize it, emplace will not work for polymorphic
> types, which IMO is one of the major use cases for unique_ptr (and a less
> major one for shared_ptr).
>
> Note: I'm not saying these are reasons I would vote against such a
> proposal; rather, these are things which need to be discussed in the
> proposal.
> --
> Nevin ":-)" Liber <mailto:ne...@eviloverlord.com <javascript:>>
> +1-847-691-1404
>
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/91fab9b2-fa08-4ee2-b71f-9c7b5c6cc690%40isocpp.org.
------=_Part_7163_1995014264.1509388361836
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">The first approach looks like this (attached).<div><br></d=
iv><div>1. Should I post it as a new topic or continue here?</div><div><br>=
</div><div>2. Should I upload it to my hosting (or some preferred one) and =
post a link or attaching the file is fine?<br><br>Thanks for your time,</di=
v><div>Vasilii Babich.<br><br>On Monday, October 30, 2017 at 8:38:37 PM UTC=
+4, Nevin ":-)" Liber wrote:<blockquote class=3D"gmail_quote" sty=
le=3D"margin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-left=
: 1ex;"><div dir=3D"ltr">On Mon, Oct 30, 2017 at 11:05 AM, <span dir=3D"lt=
r"><<a href=3D"javascript:" target=3D"_blank" gdf-obfuscated-mailto=3D"3=
mzC33oQBwAJ" rel=3D"nofollow" onmousedown=3D"this.href=3D'javascript:&#=
39;;return true;" onclick=3D"this.href=3D'javascript:';return true;=
">anta...@gmail.com</a>></span> wrote:<br><div><div class=3D"gmail_quote=
"><blockquote class=3D"gmail_quote" style=3D"margin:0 0 0 .8ex;border-left:=
1px #ccc solid;padding-left:1ex"><div dir=3D"ltr"><span><blockquote class=
=3D"gmail_quote" style=3D"margin:0;margin-left:0.8ex;border-left:1px #ccc s=
olid;padding-left:1ex"><div dir=3D"ltr"><div>void(?) unique_ptr<T>::e=
mplace(Args &&... args) { *this =3D make_unique<T>(std::forwa=
rd<<wbr>Args>(args)...); }</div><div>void(?) shared_ptr<T>::emp=
lace(Args &&... args) { *this =3D make_shared<T>(std::forward=
<<wbr>Args>(args)...); }</div></div></blockquote></span></div></block=
quote><div><br></div><div>Thoughts:</div><div><ul><li>Neither shared_ptr no=
r unique_ptr store an allocator, so shared_ptr::emplace and unique_ptr::emp=
lace are being tied to a particular allocation scheme.=C2=A0 This makes it =
harder when people refactor code to use other allocation schemes.</li><li>u=
nique_ptr has a deleter, which may not go along with emplace calling "=
new".=C2=A0 Will this function still exist if default_delete<T> =
isn't being used?<br></li><li>Unless you templatize it, emplace will no=
t work for polymorphic types, which IMO is one of the major use cases for u=
nique_ptr (and a less major one for shared_ptr).</li></ul><div>Note: =C2=A0=
I'm not saying these are reasons I would vote against such a proposal; =
rather, these are things which need to be discussed in the proposal.</div><=
/div></div>-- <br><div><div dir=3D"ltr"><div><div dir=3D"ltr"><div>=C2=A0Ne=
vin ":-)" Liber=C2=A0 <mailto:<a href=3D"javascript:" target=
=3D"_blank" gdf-obfuscated-mailto=3D"3mzC33oQBwAJ" rel=3D"nofollow" onmouse=
down=3D"this.href=3D'javascript:';return true;" onclick=3D"this.hre=
f=3D'javascript:';return true;">ne...@eviloverlord.com</a><wbr>>=
=C2=A0+1-847-691-1404</div></div></div></div></div>
</div></div>
</blockquote></div></div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/91fab9b2-fa08-4ee2-b71f-9c7b5c6cc690%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/91fab9b2-fa08-4ee2-b71f-9c7b5c6cc690=
%40isocpp.org</a>.<br />
------=_Part_7163_1995014264.1509388361836--
------=_Part_7162_1126213429.1509388361835
Content-Type: text/plain; charset=US-ASCII; name=smart_pointer_emplace_1.txt
Content-Transfer-Encoding: 7bit
Content-Disposition: attachment; filename=smart_pointer_emplace_1.txt
X-Attachment-Id: db5c7a59-f8b5-4b7d-a676-4b7ebbe8c7f1
Content-ID: <db5c7a59-f8b5-4b7d-a676-4b7ebbe8c7f1>
Date: 2017-10-30
Reply-to: Vasilii Babich <antanubis@gmail.com>
Adding Emplace functions for shared_ptr<T> / unique_ptr<T>
I. Introduction
This is a proposal to add emplace functions for standard owning shared pointers shared_ptr<T> and unique_ptr<T> as a clean way of constructing a new object that is owned by a given smart pointer similarly to the emplace function in optional<T>.
II. Motivation
A common case of creating new smart pointer values is to create a new object owned by an existing smart pointer variable whose type is exactly the type used in the smart pointer. Currently "p = make_unique<T>(args)" approach is peferred. While it eliminates one type name T from the naive approach "p = unique_ptr<T>(new T(args))" it is still unnecessary verbose, because the information about the type could be known from the pointer type itself. The proposed way of dealing with this task is to write "p.emplace(args)". The same goes for shared_ptr<T>.
III. Impact On the Standard
This proposal is library extension. It proposes adding a member function template to two standard library classes, shared_ptr and unique_ptr. It does not require any changes in the core language, and it has been implemented in standard C++. The proposal does not depend on any library extensions.
IV. Design Decisions
* The proposed library extension will improve the case of constructing the object of the exact pointed type, the mentioned "p = make_unique<T>(args)" and "p = make_shared<T>(args)".
* It will not improve the case of using custom allocators in shared_ptr.
A special "emplace_allocate(alloc, args)" method may be considered as a simplified version of "p = allocate_shared(alloc, args)".
* It will not improve the case of using custom deleter in unique_ptr.
The same goes for make_unique function, which is used to simplify the most common use case of creating a unique_ptr.
* It will not improve the case of creating an object of a derived type to be owned by a smart pointer to the base class.
In this case make_unique and make_shared are still the best option, since no unnecessary repeating is done in the code, because the desired type of the object is not known anywhere else.
The polymorphic usage of shared_ptr and unique_ptr (having a base class smart pointer that points to a derived class object) is clearly distinct from the value-type usage. The proposal improves the visual difference for this two types of usage. In the value-type usage there is no reason to prefer "= make_shared" and "= make_unique" over emplace. In polymorphic usage nothing changes and there is no reason to prefer emplace over make_* or even no way to use it.
* The proposed extension is consistent with optional<T> emplace member function which simplifies the case "o = make_optional<T>(args)" to "o.emplace(args)".
* The return type is suggested to be the reference to the smart pointer itself.
This goes well if we look at the "p.emplace(args)" as a simplified syntax for "p = make_unique<T>(args)".
Another aproach would be to return the reference to newly created object like optional<T>::emplace does. This will be consistent with the optional, but this can't be done consistently for unique_ptr<T[]> and proposed emplace(size_t n) function, because we can't get a reference to the array we hold, this unique_ptr doesn't have dereference operator.
V. Technical Specifications
Proposal:
* Add a modifier member function
template <class... Args> shared_ptr<T>& shared_ptr<T>::emplace(Args&&... args);
which effect is equivalent to
*this = make_shared<T>(args...)
* Add a modifier member function for non-array types T
template <class... Args> unique_ptr<T>& unique_ptr<T>::emplace(Args&&... args);
which effect is equivalent to
*this = make_unique<T>(args...)
* Add a modifier member function for unknown-bound array types T
unique_ptr<T>& unique_ptr<T>::emplace(size_t n);
which effect is equivalent to
*this = make_unique<T>(n);
* Add a member function for known-bound array types T
template <class... Args> unspecified unique_ptr<T>::emplace(Args&&...) = delete;
------=_Part_7162_1126213429.1509388361835--
.
Author: =?UTF-8?Q?Jonathan_M=c3=bcller?= <jonathanmueller.dev@gmail.com>
Date: Mon, 30 Oct 2017 19:36:55 +0100
Raw View
On 30.10.2017 17:37, Nevin Liber wrote:
> On Mon, Oct 30, 2017 at 11:05 AM, <antanubis@gmail.com=20
> <mailto:antanubis@gmail.com>> wrote:
>=20
> void(?) unique_ptr<T>::emplace(Args &&... args) { *this =3D
> make_unique<T>(std::forward<Args>(args)...); }
> void(?) shared_ptr<T>::emplace(Args &&... args) { *this =3D
> make_shared<T>(std::forward<Args>(args)...); }
>=20
>=20
> Thoughts:
>=20
> * Neither shared_ptr nor unique_ptr store an allocator, so
> shared_ptr::emplace and unique_ptr::emplace are being tied to a
> particular allocation scheme.=C2=A0 This makes it harder when people
> refactor code to use other allocation schemes.
> * unique_ptr has a deleter, which may not go along with emplace
> calling "new".=C2=A0 Will this function still exist if default_delete=
<T>
> isn't being used?
> * Unless you templatize it, emplace will not work for polymorphic
> types, which IMO is one of the major use cases for unique_ptr (and a
> less major one for shared_ptr).
>=20
> Note: =C2=A0I'm not saying these are reasons I would vote against such a=
=20
> proposal; rather, these are things which need to be discussed in the=20
> proposal.
Furthermore:
* The smart pointers and optional behave very differently: optional has=20
value semantics, so it makes sense to say "create a new object".
I don't think it makes sense to ask the same from unique_ptr.
* If we have `emplace()` what about a constructor of the same form?
Yes, there's make_XXX but with class template argument deduction we=20
don't really want make_XXX anymore.
* If `ptr.emplace(obj)` works, what about `ptr =3D obj`? If you say no to=
=20
assignment because it doesn't make sense, why allow emplace?
* Why go through all that just to save a `=3D make_unique<T>(blah)`?=20
That's not too much typing.
--=20
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp=
..org/d/msgid/std-proposals/ebeab15d-5424-034b-7d86-b84b381a1977%40gmail.com=
..
.
Author: antanubis@gmail.com
Date: Mon, 30 Oct 2017 12:01:03 -0700 (PDT)
Raw View
------=_Part_7040_1732903010.1509390063817
Content-Type: multipart/alternative;
boundary="----=_Part_7041_2085677401.1509390063817"
------=_Part_7041_2085677401.1509390063817
Content-Type: text/plain; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
> The smart pointers and optional behave very differently: optional has=20
value semantics, so it makes sense to say "create a new object".=20
I don't think it makes sense to ask the same from unique_ptr.=20
In my experience unique_ptr is quite similar to optional.
It is like an optional that doesn't hold the memory while there is no value=
=20
in it and that works nicely with forward declarations.
> If we have `emplace()` what about a constructor of the same form?=20
Yes, there's make_XXX but with class template argument deduction we=20
don't really want make_XXX anymore.
As I understand the smart pointer make_* methods won't go anywhere after=20
the template argument deduction comes in to play because they're not a=20
helper functions for existing constructors of smart pointers. They can=20
replace "make_unique<T>(args)" with "unique_ptr(new T(args))" with=20
returning naked new to the common pattern (which is not looking good) and=
=20
they can't replace make_shared at all because of optimized storage used in=
=20
make_shared compared to "shared_ptr(new T(args))".
If we have emplace() in smart pointers perhaps we also would like to have=
=20
in_place constructors for smart pointers similar to optional constructors=
=20
with std::in_place. Those constructors would improve the usage of member=20
initialization of smart pointer fields while emplace improves the usage of=
=20
assigning of smart pointer variables. This will allow us to use "A::A() :=
=20
p(in_place, args)" instead of "A::A() : p(make_unique<T>(args))" and=20
"p.emplace(args)" instead of "p =3D make_unique<T>(args)".
> If `ptr.emplace(obj)` works, what about `ptr =3D obj`? If you say no to=
=20
assignment because it doesn't make sense, why allow emplace?
object.emplace(value) doesn't always say "assign this value to that object"=
=20
even with exactly one argument. For example std::set<T> has=20
..emplace(value), but it doesn't allow assigning this value to it. emplace()=
=20
methods in all standard classes say something like "create a new object=20
from all those arguments and put it inside" and it works perfectly for both=
=20
shared_ptr and unique_ptr.
> Why go through all that just to save a `=3D make_unique<T>(blah)`?=20
That's not too much typing.=20
The same can be said about "make_unique", but it was added, because it is a=
=20
common pattern and it simplifies the code. "p =3D unique_ptr<T>(new T(args)=
)"=20
is more verbose than "p =3D make_unique<T>(args)" which is still unnecessar=
y=20
verbose compared to "p.emplace(args)". The amount of typing depends on the=
=20
type T. :) If we introduce "auto" to reduce unnecessary typing in favour of=
=20
better non-abbreviated type names (even if they're longer) in places where=
=20
we have to specify them, I don't see why we won't remove those unneeded=20
type name typings in other common code patterns.
On Monday, October 30, 2017 at 10:36:59 PM UTC+4, Jonathan M=C3=BCller wrot=
e:
>
> On 30.10.2017 17:37, Nevin Liber wrote:=20
> > On Mon, Oct 30, 2017 at 11:05 AM, <anta...@gmail.com <javascript:>=20
> > <mailto:anta...@gmail.com <javascript:>>> wrote:=20
> >=20
> > void(?) unique_ptr<T>::emplace(Args &&... args) { *this =3D=20
> > make_unique<T>(std::forward<Args>(args)...); }=20
> > void(?) shared_ptr<T>::emplace(Args &&... args) { *this =3D=20
> > make_shared<T>(std::forward<Args>(args)...); }=20
> >=20
> >=20
> > Thoughts:=20
> >=20
> > * Neither shared_ptr nor unique_ptr store an allocator, so=20
> > shared_ptr::emplace and unique_ptr::emplace are being tied to a=20
> > particular allocation scheme. This makes it harder when people=20
> > refactor code to use other allocation schemes.=20
> > * unique_ptr has a deleter, which may not go along with emplace=20
> > calling "new". Will this function still exist if default_delete<T>=
=20
> > isn't being used?=20
> > * Unless you templatize it, emplace will not work for polymorphic=20
> > types, which IMO is one of the major use cases for unique_ptr (and =
a=20
> > less major one for shared_ptr).=20
> >=20
> > Note: I'm not saying these are reasons I would vote against such a=20
> > proposal; rather, these are things which need to be discussed in the=20
> > proposal.=20
>
> Furthermore:=20
>
> * The smart pointers and optional behave very differently: optional has=
=20
> value semantics, so it makes sense to say "create a new object".=20
> I don't think it makes sense to ask the same from unique_ptr.=20
>
> * If we have `emplace()` what about a constructor of the same form?=20
> Yes, there's make_XXX but with class template argument deduction we=20
> don't really want make_XXX anymore.=20
>
> * If `ptr.emplace(obj)` works, what about `ptr =3D obj`? If you say no to=
=20
> assignment because it doesn't make sense, why allow emplace?=20
>
> * Why go through all that just to save a `=3D make_unique<T>(blah)`?=20
> That's not too much typing.=20
>
>
--=20
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp=
..org/d/msgid/std-proposals/8d668562-154e-4d26-9605-2973bb78f699%40isocpp.or=
g.
------=_Part_7041_2085677401.1509390063817
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">> The smart pointers and optional behave very different=
ly: optional has=C2=A0<br>value semantics, so it makes sense to say "c=
reate a new object".=C2=A0<br>I don't think it makes sense to ask =
the same from unique_ptr.=C2=A0<br><br>In my experience unique_ptr is quite=
similar to optional.<div>It is like an optional that doesn't hold the =
memory while there is no value in it and that works nicely with forward dec=
larations.<div><br></div><div>> If we have `emplace()` what about a cons=
tructor of the same form?=C2=A0<br>Yes, there's make_XXX but with class=
template argument deduction we=C2=A0<br>don't really want make_XXX any=
more.</div><div><br></div><div>As I understand the smart pointer make_* met=
hods won't go anywhere after the template argument deduction comes in t=
o play because they're not a helper functions for existing constructors=
of smart pointers. They can replace "make_unique<T>(args)"=
with "unique_ptr(new T(args))" with returning naked new to the c=
ommon pattern (which is not looking good) and they can't replace make_s=
hared at all because of optimized storage used in make_shared compared to &=
quot;shared_ptr(new T(args))".</div><div><br></div><div>If we have emp=
lace() in smart pointers perhaps we also would like to have in_place constr=
uctors for smart pointers similar to optional constructors with std::in_pla=
ce. Those constructors would improve the usage of member initialization of =
smart pointer fields while emplace improves the usage of assigning of smart=
pointer variables. This will allow us to use "A::A() : p(in_place, ar=
gs)" instead of "A::A() : p(make_unique<T>(args))" and=
"p.emplace(args)" instead of "p =3D make_unique<T>(ar=
gs)".</div><div><br>> If `ptr.emplace(obj)` works, what about `ptr =
=3D obj`? If you say no to=C2=A0<br>assignment because it doesn't make =
sense, why allow emplace?</div><div><br></div><div>object.emplace(value) do=
esn't always say "assign this value to that object" even with=
exactly one argument. For example std::set<T> has .emplace(value), b=
ut it doesn't allow assigning this value to it. emplace() methods in al=
l standard classes say something like "create a new object from all th=
ose arguments and put it inside" and it works perfectly for both share=
d_ptr and unique_ptr.</div><div><br></div><div>> Why go through all that=
just to save a `=3D make_unique<T>(blah)`?=C2=A0<br>That's not t=
oo much typing.=C2=A0</div><div><br></div><div>The same can be said about &=
quot;make_unique", but it was added, because it is a common pattern an=
d it simplifies the code. "p =3D unique_ptr<T>(new T(args))"=
; is more verbose than "p =3D make_unique<T>(args)" which i=
s still unnecessary verbose compared to "p.emplace(args)". The am=
ount of typing depends on the type T. :) If we introduce "auto" t=
o reduce unnecessary typing in favour of better non-abbreviated type names =
(even if they're longer) in places where we have to specify them, I don=
't see why we won't remove those unneeded type name typings in othe=
r common code patterns.</div><div><br>On Monday, October 30, 2017 at 10:36:=
59 PM UTC+4, Jonathan M=C3=BCller wrote:<blockquote class=3D"gmail_quote" s=
tyle=3D"margin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-le=
ft: 1ex;">On 30.10.2017 17:37, Nevin Liber wrote:
<br>> On Mon, Oct 30, 2017 at 11:05 AM, <<a href=3D"javascript:" targ=
et=3D"_blank" gdf-obfuscated-mailto=3D"7GAkd_AWBwAJ" rel=3D"nofollow" onmou=
sedown=3D"this.href=3D'javascript:';return true;" onclick=3D"this.h=
ref=3D'javascript:';return true;">anta...@gmail.com</a>=20
<br>> <mailto:<a href=3D"javascript:" target=3D"_blank" gdf-obfuscate=
d-mailto=3D"7GAkd_AWBwAJ" rel=3D"nofollow" onmousedown=3D"this.href=3D'=
javascript:';return true;" onclick=3D"this.href=3D'javascript:'=
;return true;">anta...@gmail.com</a>>> wrote:
<br>>=20
<br>> =C2=A0 =C2=A0 =C2=A0 =C2=A0 void(?) unique_ptr<T>::emplace(A=
rgs &&... args) { *this =3D
<br>> =C2=A0 =C2=A0 =C2=A0 =C2=A0 make_unique<T>(std::forward<<=
wbr>Args>(args)...); }
<br>> =C2=A0 =C2=A0 =C2=A0 =C2=A0 void(?) shared_ptr<T>::emplace(A=
rgs &&... args) { *this =3D
<br>> =C2=A0 =C2=A0 =C2=A0 =C2=A0 make_shared<T>(std::forward<<=
wbr>Args>(args)...); }
<br>>=20
<br>>=20
<br>> Thoughts:
<br>>=20
<br>> =C2=A0 * Neither shared_ptr nor unique_ptr store an allocator, so
<br>> =C2=A0 =C2=A0 shared_ptr::emplace and unique_ptr::emplace are bein=
g tied to a
<br>> =C2=A0 =C2=A0 particular allocation scheme.=C2=A0 This makes it ha=
rder when people
<br>> =C2=A0 =C2=A0 refactor code to use other allocation schemes.
<br>> =C2=A0 * unique_ptr has a deleter, which may not go along with emp=
lace
<br>> =C2=A0 =C2=A0 calling "new".=C2=A0 Will this function st=
ill exist if default_delete<T>
<br>> =C2=A0 =C2=A0 isn't being used?
<br>> =C2=A0 * Unless you templatize it, emplace will not work for polym=
orphic
<br>> =C2=A0 =C2=A0 types, which IMO is one of the major use cases for u=
nique_ptr (and a
<br>> =C2=A0 =C2=A0 less major one for shared_ptr).
<br>>=20
<br>> Note: =C2=A0I'm not saying these are reasons I would vote agai=
nst such a=20
<br>> proposal; rather, these are things which need to be discussed in t=
he=20
<br>> proposal.
<br>
<br>Furthermore:
<br>
<br>* The smart pointers and optional behave very differently: optional has=
=20
<br>value semantics, so it makes sense to say "create a new object&quo=
t;.
<br>I don't think it makes sense to ask the same from unique_ptr.
<br>
<br>* If we have `emplace()` what about a constructor of the same form?
<br>Yes, there's make_XXX but with class template argument deduction we=
=20
<br>don't really want make_XXX anymore.
<br>
<br>* If `ptr.emplace(obj)` works, what about `ptr =3D obj`? If you say no =
to=20
<br>assignment because it doesn't make sense, why allow emplace?
<br>
<br>* Why go through all that just to save a `=3D make_unique<T>(blah=
)`?=20
<br>That's not too much typing.
<br>
<br></blockquote></div></div></div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/8d668562-154e-4d26-9605-2973bb78f699%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/8d668562-154e-4d26-9605-2973bb78f699=
%40isocpp.org</a>.<br />
------=_Part_7041_2085677401.1509390063817--
------=_Part_7040_1732903010.1509390063817--
.
Author: =?UTF-8?Q?Jonathan_M=c3=bcller?= <jonathanmueller.dev@gmail.com>
Date: Mon, 30 Oct 2017 20:07:45 +0100
Raw View
On 30.10.2017 20:01, antanubis@gmail.com wrote:
> > The smart pointers and optional behave very differently: optional has
> value semantics, so it makes sense to say "create a new object".
> I don't think it makes sense to ask the same from unique_ptr.
>
> In my experience unique_ptr is quite similar to optional.
> It is like an optional that doesn't hold the memory while there is no
> value in it and that works nicely with forward declarations.
But they're not. optional has a copy constructor, deep comparison etc.
It just has a similar syntax because (for some reason) it was modelled
after a pointer.
>
> > If we have `emplace()` what about a constructor of the same form?
> Yes, there's make_XXX but with class template argument deduction we
> don't really want make_XXX anymore.
>
> As I understand the smart pointer make_* methods won't go anywhere after
> the template argument deduction comes in to play because they're not a
> helper functions for existing constructors of smart pointers. They can
> replace "make_unique<T>(args)" with "unique_ptr(new T(args))" with
> returning naked new to the common pattern (which is not looking good)
> and they can't replace make_shared at all because of optimized storage
> used in make_shared compared to "shared_ptr(new T(args))".
>
> If we have emplace() in smart pointers perhaps we also would like to
> have in_place constructors for smart pointers similar to optional
> constructors with std::in_place. Those constructors would improve the
> usage of member initialization of smart pointer fields while emplace
> improves the usage of assigning of smart pointer variables. This will
> allow us to use "A::A() : p(in_place, args)" instead of "A::A() :
> p(make_unique<T>(args))" and "p.emplace(args)" instead of "p =
> make_unique<T>(args)".
>
This in place constructor is exactly what I meant there.
My comment is meant to be read as "will you also propose an in-place
constructor?"
> > If `ptr.emplace(obj)` works, what about `ptr = obj`? If you say no to
> assignment because it doesn't make sense, why allow emplace?
>
> object.emplace(value) doesn't always say "assign this value to that
> object" even with exactly one argument. For example std::set<T> has
> .emplace(value), but it doesn't allow assigning this value to it.
> emplace() methods in all standard classes say something like "create a
> new object from all those arguments and put it inside" and it works
> perfectly for both shared_ptr and unique_ptr.
It doesn't mean that but should you also add a corresponding `operator=`?
---
I think you are trying to turn smart pointers into indirect<T>, which is
already proposed:
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2016/p0201r1.pdf
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/b59f31eb-2efa-71ed-5b9b-460dcf3741d3%40gmail.com.
.
Author: antanubis@gmail.com
Date: Mon, 30 Oct 2017 13:17:42 -0700 (PDT)
Raw View
------=_Part_2145_1497297990.1509394662096
Content-Type: multipart/alternative;
boundary="----=_Part_2146_1786969177.1509394662096"
------=_Part_2146_1786969177.1509394662096
Content-Type: text/plain; charset="UTF-8"
> But they're not. optional has a copy constructor, deep comparison etc.
It just has a similar syntax because (for some reason) it was modelled
after a pointer.
Even if we're speaking only about similarities in syntax, they're still
similarities. Not only operator*(), operator->() and explicit operator
bool(), but also reset() member function and make_*<T>(constructor_args)
free function. And I see the emplace() method and in place constructors as
good candidates for syntax similarities as well.
> This in place constructor is exactly what I meant there.
My comment is meant to be read as "will you also propose an in-place
constructor?"
Yes, I think in-place constructor could be a good addition to such proposal.
> It doesn't mean that but should you also add a corresponding `operator=`?
No, in my opinion assignment is not related to the emplace() function and I
do not think it should be added to smart pointers. A case with
single-argument emplace() call is just one case of a usual emplace() usage
that takes arbitrary number and types of constructor arguments. Assignment
a value to a smart pointer will just confuse everyone without adding
anything, because "*p = value" syntax doesn't have any problems and is very
similar to "p = value" syntax.
> I think you are trying to turn smart pointers into indirect<T>
I don't think so, indirect<T> solves its own goal of a deep-copyable
indirect (possibly polymorphic) value type (being already renamed to
polymorphic_value in the reference implementation).
All those wrapper classes (optional, shared_ptr, unique_ptr, indirect)
serve different goals, but they all can contain a value of the type
specified in the template parameter, they all share some of the public
interface (like reset() call, like smart pointer semantics, like make_*
helpers) - and I think they all should have similar interface to construct
a new such value in the most efficient way, in both cases - when
constructing a new wrapper object and when changing an existing wrapper
object. First can be achieved by in_place constructors, second can be
achieved by emplace() call.
For shared_ptr make_shared encapsulates the most-used case (not custom
allocator), hiding the explicit "new" and "delete" calls. The "emplace"
method and in_place constructor achieve the same but with more clear syntax
(no repeating of the type name) and possibly more efficient (no move
constructor / assigning).
For unique_ptr make_unique encapsulates the most-used case (not custom
deleter), hiding the explicit "new" and "delete" calls. The same arguments
go for "emplace" and in_place constructor here as for shared_ptr. If you
use custom deleter, then it is likely you don't need the make function
anyway, because the object is likely to be constructed somewhere else, not
by a plain "new" call.
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/281e79ef-e1f7-45c2-8b72-ed5c49392180%40isocpp.org.
------=_Part_2146_1786969177.1509394662096
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">> But they're not. optional has a copy constructor,=
deep comparison etc.=C2=A0<br>It just has a similar syntax because (for so=
me reason) it was modelled=C2=A0<br>after a pointer.=C2=A0<br><br>Even if w=
e're speaking only about similarities in syntax, they're still simi=
larities. Not only operator*(), operator->() and explicit operator bool(=
), but also reset() member function and make_*<T>(constructor_args) f=
ree function. And I see the emplace() method and in place constructors as g=
ood candidates for syntax similarities as well.<div><br></div><div>> Thi=
s in place constructor is exactly what I meant there.=C2=A0<br>My comment i=
s meant to be read as "will you also propose an in-place=C2=A0<br>cons=
tructor?"=C2=A0</div><div><br></div><div>Yes, I think in-place constru=
ctor could be a good addition to such proposal.</div><div><br></div><div>&g=
t; It doesn't mean that but should you also add a corresponding `operat=
or=3D`?=C2=A0</div><div><br></div><div>No, in my opinion assignment is not =
related to the emplace() function and I do not think it should be added to =
smart pointers. A case with single-argument emplace() call is just one case=
of a usual emplace() usage that takes arbitrary number and types of constr=
uctor arguments. Assignment a value to a smart pointer will just confuse ev=
eryone without adding anything, because "*p =3D value" syntax doe=
sn't have any problems and is very similar to "p =3D value" s=
yntax.<br><br>> I think you are trying to turn smart pointers into indir=
ect<T></div><div><br></div><div>I don't think so, indirect<T&g=
t; solves its own goal of a deep-copyable indirect (possibly polymorphic) v=
alue type (being already renamed to polymorphic_value in the reference impl=
ementation).</div><div><br></div><div>All those wrapper classes (optional, =
shared_ptr, unique_ptr, indirect) serve different goals, but they all can c=
ontain a value of the type specified in the template parameter, they all sh=
are some of the public interface (like reset() call, like smart pointer sem=
antics, like make_* helpers) - and I think they all should have similar int=
erface to construct a new such value in the most efficient way, in both cas=
es - when constructing a new wrapper object and when changing an existing w=
rapper object. First can be achieved by in_place constructors, second can b=
e achieved by emplace() call.</div><div><br></div><div>For shared_ptr make_=
shared encapsulates the most-used case (not custom allocator), hiding the e=
xplicit "new" and "delete" calls. The "emplace&quo=
t; method and in_place constructor achieve the same but with more clear syn=
tax (no repeating of the type name) and possibly more efficient (no move co=
nstructor / assigning).</div><div><br></div><div>For unique_ptr make_unique=
encapsulates the most-used case (not custom deleter), hiding the explicit =
"new" and "delete" calls. The same arguments go for &qu=
ot;emplace" and in_place constructor here as for shared_ptr. If you us=
e custom deleter, then it is likely you don't need the make function an=
yway, because the object is likely to be constructed somewhere else, not by=
a plain "new" call.</div><div><br></div></div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/281e79ef-e1f7-45c2-8b72-ed5c49392180%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/281e79ef-e1f7-45c2-8b72-ed5c49392180=
%40isocpp.org</a>.<br />
------=_Part_2146_1786969177.1509394662096--
------=_Part_2145_1497297990.1509394662096--
.
Author: Arthur O'Dwyer <arthur.j.odwyer@gmail.com>
Date: Mon, 30 Oct 2017 16:03:43 -0700 (PDT)
Raw View
------=_Part_7274_472954870.1509404623772
Content-Type: multipart/alternative;
boundary="----=_Part_7275_213260885.1509404623772"
------=_Part_7275_213260885.1509404623772
Content-Type: text/plain; charset="UTF-8"
On Monday, October 30, 2017 at 9:01:25 AM UTC-7, anta...@gmail.com wrote:
>
> I've found really helpful in my own smart pointer classes to have
> something like .create(Args &&..args) method that creates an object for an
> owning shared pointer without the necessity for repeating the type in the
> make_* non-member function.
>
> It's a shame that standard smart pointers don't have such method, so in
> order to create a value you always need to repeat the type name, while it
> is contained in the pointer type itself.
>
Technically, you're not "repeating" the type, since you name it only once.
Remember that C++ supports classical object-oriented programming; I would
even go so far as to claim that heap-allocating single objects is a pattern
*primarily* used by classical OO programmers. So we are talking about
std::unique_ptr<Widget> mPtr; // ...
this->mPtr = std::make_unique<WidgetImpl>(some, args);
And you're proposing to rewrite that as something like
std::unique_ptr<Widget> mPtr; // ...
this->mPtr.emplace<WidgetImpl>(some, args);
I don't see that as a valuable use of your time.
> void(?) unique_ptr<T>::emplace(Args &&... args) { *this =
> make_unique<T>(std::forward<Args>(args)...); }
> void(?) shared_ptr<T>::emplace(Args &&... args) { *this =
> make_shared<T>(std::forward<Args>(args)...); }
>
> What do you think? Are there reasons not to add such methods? Or was this
> discussed / proposed already?
>
You should avoid adding a hard dependency between std::unique_ptr<T,D> and
std::shared_ptr<T> on the one hand, and the global new/delete heap used by
make_unique and make_shared on the other. Right now it's possible to use
unique_ptr and shared_ptr with custom deleters for purposes other than
classical OO. Creating a *member function interface* that is useful only
for your specific use-case strikes me as going somewhat against the "C++
spirit" of small classes that provide a complete and orthogonal set of
accessors.
Also, I personally find it easier to reason about value semantics than
object semantics. Rather than think of "unique_ptr<T> p" as an object in
memory that I "mutate" via member functions, I try to think of it more like
an abstract *label* for a particular pointer *value* that I've created. So
for me,
p = make_unique<T>(some, args);
// do some stuff
p = nullptr;
perfectly captures my mental model of how pointers behave. I specifically
avoid writing "object-semantic" code such as
p.reset(new T(some, args)); // or p.emplace(some, args);
// do some stuff
p.reset();
even though it gives exactly the same codegen; I just find the
value-semantic version easier to reason about.
HTH,
Arthur
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/fbefe918-b89a-4d5f-83c9-c25806e758bd%40isocpp.org.
------=_Part_7275_213260885.1509404623772
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">On Monday, October 30, 2017 at 9:01:25 AM UTC-7, anta...@g=
mail.com wrote:<blockquote class=3D"gmail_quote" style=3D"margin: 0;margin-=
left: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;"><div dir=3D"ltr=
"><div>I've found really helpful in my own smart pointer classes to hav=
e something like .create(Args &&..args) method that creates an obje=
ct for an owning shared pointer without the necessity for repeating the typ=
e in the make_* non-member function.</div><div><br></div><div>It's a sh=
ame that standard smart pointers don't have such method, so in order to=
create a value you always need to repeat the type name, while it is contai=
ned in the pointer type itself.</div></div></blockquote><div><br></div><div=
>Technically, you're not "repeating" the type, since you name=
it only once.</div><div>Remember that C++ supports classical object-orient=
ed programming; I would even go so far as to claim that heap-allocating sin=
gle objects is a pattern <i>primarily</i> used by classical OO programmers.=
So we are talking about</div><div><br></div><div>=C2=A0 =C2=A0 std::unique=
_ptr<Widget> mPtr; =C2=A0// ...</div><div>=C2=A0 =C2=A0 this->mPtr=
=3D std::make_unique<WidgetImpl>(some, args);</div><div><br></div><d=
iv>And you're proposing to rewrite that as something like</div><div><br=
></div><div><div>=C2=A0 =C2=A0 std::unique_ptr<Widget> mPtr; =C2=A0//=
...</div><div>=C2=A0 =C2=A0 this->mPtr.emplace<WidgetImpl>(some, =
args);</div><div><br></div><div>I don't see that as a valuable use of y=
our time.</div></div><div>=C2=A0</div><blockquote class=3D"gmail_quote" sty=
le=3D"margin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-left=
: 1ex;"><div dir=3D"ltr"><div>void(?) unique_ptr<T>::emplace(Args &am=
p;&... args) { *this =3D make_unique<T>(std::forward<<wbr>Args=
>(args)...); }<br></div><div>void(?) shared_ptr<T>::emplace(Args &=
amp;&... args) { *this =3D make_shared<T>(std::forward<<wbr>Ar=
gs>(args)...); }</div><div><br></div><div>What do you think? Are there r=
easons not to add such methods? Or was this discussed / proposed already?</=
div></div></blockquote><div><br></div><div>You should avoid adding a hard d=
ependency between std::unique_ptr<T,D> and std::shared_ptr<T> o=
n the one hand, and the global new/delete heap used by make_unique and make=
_shared on the other. Right now it's possible to use unique_ptr and sha=
red_ptr with custom deleters for purposes other than classical OO. Creating=
a <i>member function interface</i> that is useful only for your specific u=
se-case strikes me as going somewhat against the "C++ spirit" of =
small classes that provide a complete and orthogonal set of accessors.</div=
><div><br></div><div><br></div><div>Also, I personally find it easier to re=
ason about value semantics than object semantics. Rather than think of &quo=
t;unique_ptr<T> p" as an object in memory that I "mutate&qu=
ot; via member functions, I try to think of it more like an abstract=C2=A0<=
i>label</i> for a particular pointer <i>value</i> that I've created. So=
for me,</div><div><br></div><div>=C2=A0 =C2=A0 p =3D make_unique<T>(=
some, args);</div><div>=C2=A0 =C2=A0 // do some stuff</div><div>=C2=A0 =C2=
=A0 p =3D nullptr;</div><div><br></div><div>perfectly captures my mental mo=
del of how pointers behave. I specifically avoid writing "object-seman=
tic" code such as</div><div><br></div><div>=C2=A0 =C2=A0 p.reset(new T=
(some, args)); =C2=A0// or p.emplace(some, args);</div><div>=C2=A0 =C2=A0 /=
/ do some stuff</div><div>=C2=A0 =C2=A0 p.reset();</div><div><br></div><div=
>even though it gives exactly the same codegen; I just find the value-seman=
tic version easier to reason about.</div><div><br></div><div>HTH,</div><div=
>Arthur</div></div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/fbefe918-b89a-4d5f-83c9-c25806e758bd%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/fbefe918-b89a-4d5f-83c9-c25806e758bd=
%40isocpp.org</a>.<br />
------=_Part_7275_213260885.1509404623772--
------=_Part_7274_472954870.1509404623772--
.
Author: =?UTF-8?Q?=27Thomas_K=C3=B6ppe=27_via_ISO_C=2B=2B_Standard_=2D_Future_Proposals?= <std-proposals@isocpp.org>
Date: Tue, 31 Oct 2017 07:33:54 -0700 (PDT)
Raw View
------=_Part_8392_874035794.1509460434777
Content-Type: multipart/alternative;
boundary="----=_Part_8393_1744983977.1509460434777"
------=_Part_8393_1744983977.1509460434777
Content-Type: text/plain; charset="UTF-8"
It seems to me that emplacement should be provided by the deleter, since
the deleter does the matching deleting. So perhaps a more fruitful pursuit
would be to add an "emplace" to the deleter, and then have the unique_ptr's
delete forward to *that*.
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/a30180ed-684d-440d-af4a-ad8aa2e6b3a4%40isocpp.org.
------=_Part_8393_1744983977.1509460434777
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">It seems to me that emplacement should be provided by the =
deleter, since the deleter does the matching deleting. So perhaps a more fr=
uitful pursuit would be to add an "emplace" to the deleter, and t=
hen have the unique_ptr's delete forward to <i>that</i>.</div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/a30180ed-684d-440d-af4a-ad8aa2e6b3a4%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/a30180ed-684d-440d-af4a-ad8aa2e6b3a4=
%40isocpp.org</a>.<br />
------=_Part_8393_1744983977.1509460434777--
------=_Part_8392_874035794.1509460434777--
.
Author: Tony V E <tvaneerd@gmail.com>
Date: Tue, 31 Oct 2017 11:01:40 -0400
Raw View
<html><head></head><body lang=3D"en-US" style=3D"background-color: rgb(255,=
255, 255); line-height: initial;"> =
<div style=3D"width: 100%; fo=
nt-size: initial; font-family: Calibri, 'Slate Pro', sans-serif, sans-serif=
; color: rgb(31, 73, 125); text-align: initial; background-color: rgb(255, =
255, 255);">And I was wondering if emplace was going to reuse the existing =
memory (when available) and that might also require coordination with the d=
eleter.</div><div style=3D"width: 100%; font-size: initial; font-family: Ca=
libri, 'Slate Pro', sans-serif, sans-serif; color: rgb(31, 73, 125); text-a=
lign: initial; background-color: rgb(255, 255, 255);"><br></div><div style=
=3D"width: 100%; font-size: initial; font-family: Calibri, 'Slate Pro', san=
s-serif, sans-serif; color: rgb(31, 73, 125); text-align: initial; backgrou=
nd-color: rgb(255, 255, 255);">Also, unique_ptr supports =E2=80=8Efancy poi=
nters. Keep that in mind.</div> =
=
<div style=3D"width: 100%; font-size: initial; font-family: C=
alibri, 'Slate Pro', sans-serif, sans-serif; color: rgb(31, 73, 125); text-=
align: initial; background-color: rgb(255, 255, 255);"><br style=3D"display=
:initial"></div> =
=
<div style=3D"=
font-size: initial; font-family: Calibri, 'Slate Pro', sans-serif, sans-ser=
if; color: rgb(31, 73, 125); text-align: initial; background-color: rgb(255=
, 255, 255);">Sent from my BlackBerry portable Bab=
bage Device</div> =
=
<table width=3D"100%" sty=
le=3D"background-color:white;border-spacing:0px;"> <tbody><tr><td colspan=
=3D"2" style=3D"font-size: initial; text-align: initial; background-color: =
rgb(255, 255, 255);"> <div style=3D"border-style:=
solid none none; border-top-color: rgb(181, 196, 223); border-top-width: 1=
pt; padding: 3pt 0in 0in; font-family: Tahoma, 'BB Alpha Sans', 'Slate Pro'=
; font-size: 10pt;"> <div><b>From: </b>'Thomas K=C3=B6ppe' via ISO C++ Sta=
ndard - Future Proposals</div><div><b>Sent: </b>Tuesday, October 31, 2017 1=
0:33 AM</div><div><b>To: </b>ISO C++ Standard - Future Proposals</div><div>=
<b>Reply To: </b>std-proposals@isocpp.org</div><div><b>Cc: </b>antanubis@gm=
ail.com</div><div><b>Subject: </b>[std-proposals] Re: Add .emplace() method=
to std::unique_ptr and std::shared_ptr like it is in std::optional.</div><=
/div></td></tr></tbody></table><div style=3D"border-style: solid none none;=
border-top-color: rgb(186, 188, 209); border-top-width: 1pt; font-size: in=
itial; text-align: initial; background-color: rgb(255, 255, 255);"></div><b=
r><div id=3D"_originalContent" style=3D""><div dir=3D"ltr">It seems to me t=
hat emplacement should be provided by the deleter, since the deleter does t=
he matching deleting. So perhaps a more fruitful pursuit would be to add an=
"emplace" to the deleter, and then have the unique_ptr's delete forward to=
<i>that</i>.</div>
<p></p>
-- <br>
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.<br>
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br>
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br>
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/a30180ed-684d-440d-af4a-ad8aa2e6b3a4%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.goo=
gle.com/a/isocpp.org/d/msgid/std-proposals/a30180ed-684d-440d-af4a-ad8aa2e6=
b3a4%40isocpp.org</a>.<br>
<br><!--end of _originalContent --></div></body></html>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/20171031150140.5156944.20370.38945%40=
gmail.com?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.com=
/a/isocpp.org/d/msgid/std-proposals/20171031150140.5156944.20370.38945%40gm=
ail.com</a>.<br />
.
Author: Victor Dyachenko <victor.dyachenko@gmail.com>
Date: Wed, 1 Nov 2017 04:30:14 -0700 (PDT)
Raw View
------=_Part_10244_855319364.1509535814720
Content-Type: multipart/alternative;
boundary="----=_Part_10245_1351524308.1509535814720"
------=_Part_10245_1351524308.1509535814720
Content-Type: text/plain; charset="UTF-8"
Similar discussion:
https://groups.google.com/a/isocpp.org/forum/#!topic/std-proposals/Gx02KuYNIPY
--
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
To view this discussion on the web visit https://groups.google.com/a/isocpp.org/d/msgid/std-proposals/8a2f75f8-308a-4415-9fab-95a44be8e0bd%40isocpp.org.
------=_Part_10245_1351524308.1509535814720
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">Similar discussion: https://groups.google.com/a/isocpp.org=
/forum/#!topic/std-proposals/Gx02KuYNIPY</div>
<p></p>
-- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals" group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
To view this discussion on the web visit <a href=3D"https://groups.google.c=
om/a/isocpp.org/d/msgid/std-proposals/8a2f75f8-308a-4415-9fab-95a44be8e0bd%=
40isocpp.org?utm_medium=3Demail&utm_source=3Dfooter">https://groups.google.=
com/a/isocpp.org/d/msgid/std-proposals/8a2f75f8-308a-4415-9fab-95a44be8e0bd=
%40isocpp.org</a>.<br />
------=_Part_10245_1351524308.1509535814720--
------=_Part_10244_855319364.1509535814720--
.