Topic: Bulk insertion support for vector
Author: Brent Friedman <fourthgeek@gmail.com>
Date: Sat, 31 Oct 2015 21:09:49 -0500
Raw View
--047d7b41c680d28c85052371272a
Content-Type: text/plain; charset=UTF-8
Hello,
I just implemented something in our own vector-like container which looks
like it will be a really useful simplification + optimization. I'm curious
as to if anyone is familiar with similar approaches.
To our vector class I added the function "accomodate_back". This function
reserves memory in the vector but does not initialize that memory. Instead,
it returns a raw_storage_range which is a range for raw_storage_iterator.
We can now pass that range into algorithms and generate the values
ourselves.
For example, given:
A)
> vec.reserve(100);
> for (int i=0; i<100; ++i)
> {
> vec.push_back( get() );
> }
with this code, the ranges TS, and a few additional changes we can write:
B)
> std::generate( vec.accomodate_back(100), [&]{return get(); });
We basically allocate room for 100 elements and then placement new them in
a loop.
In the case of B), the amortized growth of push_back is completely
eliminated and the compiler doesn't have to emit code to handle the growth
for each loop iteration. This approach also eliminates code duplication
(repeated uses of 'vec' and '100').
Chandler Carruth mentioned in this video that optimizing out the amortized
growth pattern of push_back was very difficult. Maybe we can write our code
in a way that is easier to read and optimize instead. Grow once, then
construct separately.
https://www.irill.org/videos/euro-llvm-2013/carruth-hires
One small issue is that, in order to be compatible with most algorithms,
raw_storage_iterator needs to be upgraded from an OutputIterator to a
ForwardIterator.
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
--047d7b41c680d28c85052371272a
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">Hello,<div><br></div><div>I just implemented something in =
our own vector-like container which looks like it will be a really useful s=
implification + optimization. I'm curious as to if anyone is familiar w=
ith similar approaches.</div><div><br></div><div>To our vector class I adde=
d the function "accomodate_back". This function reserves memory i=
n the vector but does not initialize that memory. Instead, it returns a raw=
_storage_range which is a range for raw_storage_iterator. We can now pass t=
hat range into algorithms and generate the values ourselves.</div><div><br>=
</div><div>For example, given:</div><div>A)</div><blockquote class=3D"gmail=
_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left=
-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">vec.reser=
ve(100);<br>for (int i=3D0; i<100; ++i)<br>{<br>=C2=A0 =C2=A0vec.push_ba=
ck( get() );<br>}</blockquote><div><br></div><div>with this code, the range=
s TS, and a few additional changes we can write:</div><div>B)</div><blockqu=
ote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left-wid=
th:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-l=
eft:1ex">std::generate( vec.accomodate_back(100), [&]{return get(); });=
</blockquote><div><br></div><div>We basically allocate room for 100 element=
s and then placement new them in a loop.</div><div><br></div><div>In the ca=
se of B), the amortized growth of push_back is completely eliminated and th=
e compiler doesn't have to emit code to handle the growth for each loop=
iteration. This approach also eliminates code duplication (repeated uses o=
f 'vec' and '100').</div><div><br></div><div>Chandler Carru=
th mentioned in this video that optimizing out the amortized growth pattern=
of push_back was very difficult. Maybe we can write our code in a way that=
is easier to read and optimize instead. Grow once, then construct separate=
ly.</div><div><a href=3D"https://www.irill.org/videos/euro-llvm-2013/carrut=
h-hires">https://www.irill.org/videos/euro-llvm-2013/carruth-hires</a><br><=
/div><div><br></div><div>One small issue is that, in order to be compatible=
with most algorithms, raw_storage_iterator needs to be upgraded from an Ou=
tputIterator to a ForwardIterator.</div></div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
--047d7b41c680d28c85052371272a--
.
Author: Brent Friedman <fourthgeek@gmail.com>
Date: Sat, 31 Oct 2015 22:40:55 -0500
Raw View
--047d7b33d2de9c7e5a0523726d61
Content-Type: text/plain; charset=UTF-8
It's hard to measure the difference accurately without an actual
implementation in vector, but I created a test case here to demonstrate
what we might expect the difference to be:
https://goo.gl/Eb3M8Z
The reserve + push_back version emits 234 lines of assembly while the
reserve + placement new version emits 14 lines of assembly. So that's
pretty good.
On Sat, Oct 31, 2015 at 9:09 PM, Brent Friedman <fourthgeek@gmail.com>
wrote:
> Hello,
>
> I just implemented something in our own vector-like container which looks
> like it will be a really useful simplification + optimization. I'm curious
> as to if anyone is familiar with similar approaches.
>
> To our vector class I added the function "accomodate_back". This function
> reserves memory in the vector but does not initialize that memory. Instead,
> it returns a raw_storage_range which is a range for raw_storage_iterator.
> We can now pass that range into algorithms and generate the values
> ourselves.
>
> For example, given:
> A)
>
>> vec.reserve(100);
>> for (int i=0; i<100; ++i)
>> {
>> vec.push_back( get() );
>> }
>
>
> with this code, the ranges TS, and a few additional changes we can write:
> B)
>
>> std::generate( vec.accomodate_back(100), [&]{return get(); });
>
>
> We basically allocate room for 100 elements and then placement new them in
> a loop.
>
> In the case of B), the amortized growth of push_back is completely
> eliminated and the compiler doesn't have to emit code to handle the growth
> for each loop iteration. This approach also eliminates code duplication
> (repeated uses of 'vec' and '100').
>
> Chandler Carruth mentioned in this video that optimizing out the amortized
> growth pattern of push_back was very difficult. Maybe we can write our code
> in a way that is easier to read and optimize instead. Grow once, then
> construct separately.
> https://www.irill.org/videos/euro-llvm-2013/carruth-hires
>
> One small issue is that, in order to be compatible with most algorithms,
> raw_storage_iterator needs to be upgraded from an OutputIterator to a
> ForwardIterator.
>
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
--047d7b33d2de9c7e5a0523726d61
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">It's hard to measure the difference accurately without=
an actual implementation in vector, but I created a test case here to demo=
nstrate what we might expect the difference to be:<div><a href=3D"https://g=
oo.gl/Eb3M8Z">https://goo.gl/Eb3M8Z</a><br></div><div><br></div><div>The re=
serve + push_back version emits 234 lines of assembly while the reserve + p=
lacement new version emits 14 lines of assembly. So that's pretty good.=
</div></div><div class=3D"gmail_extra"><br><div class=3D"gmail_quote">On Sa=
t, Oct 31, 2015 at 9:09 PM, Brent Friedman <span dir=3D"ltr"><<a href=3D=
"mailto:fourthgeek@gmail.com" target=3D"_blank">fourthgeek@gmail.com</a>>=
;</span> wrote:<br><blockquote class=3D"gmail_quote" style=3D"margin:0 0 0 =
..8ex;border-left:1px #ccc solid;padding-left:1ex"><div dir=3D"ltr">Hello,<d=
iv><br></div><div>I just implemented something in our own vector-like conta=
iner which looks like it will be a really useful simplification + optimizat=
ion. I'm curious as to if anyone is familiar with similar approaches.</=
div><div><br></div><div>To our vector class I added the function "acco=
modate_back". This function reserves memory in the vector but does not=
initialize that memory. Instead, it returns a raw_storage_range which is a=
range for raw_storage_iterator. We can now pass that range into algorithms=
and generate the values ourselves.</div><div><br></div><div>For example, g=
iven:</div><div>A)</div><blockquote class=3D"gmail_quote" style=3D"margin:0=
px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);b=
order-left-style:solid;padding-left:1ex">vec.reserve(100);<br>for (int i=3D=
0; i<100; ++i)<br>{<br>=C2=A0 =C2=A0vec.push_back( get() );<br>}</blockq=
uote><div><br></div><div>with this code, the ranges TS, and a few additiona=
l changes we can write:</div><div>B)</div><blockquote class=3D"gmail_quote"=
style=3D"margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:=
rgb(204,204,204);border-left-style:solid;padding-left:1ex">std::generate( v=
ec.accomodate_back(100), [&]{return get(); });</blockquote><div><br></d=
iv><div>We basically allocate room for 100 elements and then placement new =
them in a loop.</div><div><br></div><div>In the case of B), the amortized g=
rowth of push_back is completely eliminated and the compiler doesn't ha=
ve to emit code to handle the growth for each loop iteration. This approach=
also eliminates code duplication (repeated uses of 'vec' and '=
100').</div><div><br></div><div>Chandler Carruth mentioned in this vide=
o that optimizing out the amortized growth pattern of push_back was very di=
fficult. Maybe we can write our code in a way that is easier to read and op=
timize instead. Grow once, then construct separately.</div><div><a href=3D"=
https://www.irill.org/videos/euro-llvm-2013/carruth-hires" target=3D"_blank=
">https://www.irill.org/videos/euro-llvm-2013/carruth-hires</a><br></div><d=
iv><br></div><div>One small issue is that, in order to be compatible with m=
ost algorithms, raw_storage_iterator needs to be upgraded from an OutputIte=
rator to a ForwardIterator.</div></div>
</blockquote></div><br></div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
--047d7b33d2de9c7e5a0523726d61--
.
Author: Nicol Bolas <jmckesson@gmail.com>
Date: Sat, 31 Oct 2015 21:04:16 -0700 (PDT)
Raw View
------=_Part_2282_791745502.1446350656773
Content-Type: multipart/alternative;
boundary="----=_Part_2283_410194683.1446350656773"
------=_Part_2283_410194683.1446350656773
Content-Type: text/plain; charset=UTF-8
On Saturday, October 31, 2015 at 11:40:57 PM UTC-4, Brent Friedman wrote:
>
> It's hard to measure the difference accurately without an actual
> implementation in vector, but I created a test case here to demonstrate
> what we might expect the difference to be:
> https://goo.gl/Eb3M8Z
>
> The reserve + push_back version emits 234 lines of assembly while the
> reserve + placement new version emits 14 lines of assembly. So that's
> pretty good.
>
Considering the fact that they're not doing the same work, that proves
nothing. The "reserve + placement new" is not updating the internal state
of the vector, for example.
I see no reason for a "range" to be applied here. This is best done as a
specialized algorithm, set as a member function of `vector`. It would have
versions to repeatedly call the given function (`generate_n`) or extract
elements from a range (`copy`). But they would explicitly allocate the
range, and any modifications to the vector made by the range would result
in undefined behavior.
I think that's much better than defining some kind of output range type for
this.
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
------=_Part_2283_410194683.1446350656773
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr"><br><br>On Saturday, October 31, 2015 at 11:40:57 PM UTC-4=
, Brent Friedman wrote:<blockquote class=3D"gmail_quote" style=3D"margin: 0=
;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;"><div di=
r=3D"ltr">It's hard to measure the difference accurately without an act=
ual implementation in vector, but I created a test case here to demonstrate=
what we might expect the difference to be:<div><a href=3D"https://goo.gl/E=
b3M8Z" target=3D"_blank" rel=3D"nofollow" onmousedown=3D"this.href=3D'h=
ttps://goo.gl/Eb3M8Z';return true;" onclick=3D"this.href=3D'https:/=
/goo.gl/Eb3M8Z';return true;">https://goo.gl/Eb3M8Z</a><br></div><div><=
br></div><div>The reserve + push_back version emits 234 lines of assembly w=
hile the reserve + placement new version emits 14 lines of assembly. So tha=
t's pretty good.</div></div></blockquote><div><br>Considering the fact =
that they're not doing the same work, that proves nothing. The "re=
serve + placement new" is not updating the internal state of the vecto=
r, for example.<br><br>I see no reason for a "range" to be applie=
d here. This is best done as a specialized algorithm, set as a member funct=
ion of `vector`. It would have versions to repeatedly call the given functi=
on (`generate_n`) or extract elements from a range (`copy`). But they would=
explicitly allocate the range, and any modifications to the vector made by=
the range would result in undefined behavior.<br><br>I think that's mu=
ch better than defining some kind of output range type for this.<br></div><=
/div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
------=_Part_2283_410194683.1446350656773--
------=_Part_2282_791745502.1446350656773--
.
Author: Brent Friedman <fourthgeek@gmail.com>
Date: Sat, 31 Oct 2015 23:07:07 -0500
Raw View
--047d7b3a960a4ee233052372cb6d
Content-Type: text/plain; charset=UTF-8
>
> Considering the fact that they're not doing the same work, that proves
> nothing. The "reserve + placement new" is not updating the internal state
> of the vector, for example.
What internal state is it not updating? The "end" pointer does not require
200 assembly instructions to set. And from reading the code, reserve +
placement new is hitting the important high notes. It's allocating memory,
assigning the values, and deleting the memory.
On Sat, Oct 31, 2015 at 11:04 PM, Nicol Bolas <jmckesson@gmail.com> wrote:
>
>
> On Saturday, October 31, 2015 at 11:40:57 PM UTC-4, Brent Friedman wrote:
>>
>> It's hard to measure the difference accurately without an actual
>> implementation in vector, but I created a test case here to demonstrate
>> what we might expect the difference to be:
>> https://goo.gl/Eb3M8Z
>>
>> The reserve + push_back version emits 234 lines of assembly while the
>> reserve + placement new version emits 14 lines of assembly. So that's
>> pretty good.
>>
>
> Considering the fact that they're not doing the same work, that proves
> nothing. The "reserve + placement new" is not updating the internal state
> of the vector, for example.
>
> I see no reason for a "range" to be applied here. This is best done as a
> specialized algorithm, set as a member function of `vector`. It would have
> versions to repeatedly call the given function (`generate_n`) or extract
> elements from a range (`copy`). But they would explicitly allocate the
> range, and any modifications to the vector made by the range would result
> in undefined behavior.
>
> I think that's much better than defining some kind of output range type
> for this.
>
> --
>
> ---
> 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.
> Visit this group at
> http://groups.google.com/a/isocpp.org/group/std-proposals/.
>
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
--047d7b3a960a4ee233052372cb6d
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr"><blockquote class=3D"gmail_quote" style=3D"margin:0px 0px =
0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-l=
eft-style:solid;padding-left:1ex"><span style=3D"font-size:12.8px">Consider=
ing the fact that they're not doing the same work, that proves nothing.=
The "reserve + placement new" is not updating the internal state=
of the vector, for example.</span></blockquote><div>What internal state is=
it not updating? The "end" pointer does not require 200 assembly=
instructions to set. And from reading the code, reserve + placement new is=
hitting the important high notes. It's allocating memory, assigning th=
e values, and deleting the memory.<br></div></div><div class=3D"gmail_extra=
"><br><div class=3D"gmail_quote">On Sat, Oct 31, 2015 at 11:04 PM, Nicol Bo=
las <span dir=3D"ltr"><<a href=3D"mailto:jmckesson@gmail.com" target=3D"=
_blank">jmckesson@gmail.com</a>></span> wrote:<br><blockquote class=3D"g=
mail_quote" style=3D"margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-l=
eft:1ex"><div dir=3D"ltr"><span class=3D""><br><br>On Saturday, October 31,=
2015 at 11:40:57 PM UTC-4, Brent Friedman wrote:<blockquote class=3D"gmail=
_quote" style=3D"margin:0;margin-left:0.8ex;border-left:1px #ccc solid;padd=
ing-left:1ex"><div dir=3D"ltr">It's hard to measure the difference accu=
rately without an actual implementation in vector, but I created a test cas=
e here to demonstrate what we might expect the difference to be:<div><a hre=
f=3D"https://goo.gl/Eb3M8Z" rel=3D"nofollow" target=3D"_blank">https://goo.=
gl/Eb3M8Z</a><br></div><div><br></div><div>The reserve + push_back version =
emits 234 lines of assembly while the reserve + placement new version emits=
14 lines of assembly. So that's pretty good.</div></div></blockquote><=
/span><div><br>Considering the fact that they're not doing the same wor=
k, that proves nothing. The "reserve + placement new" is not upda=
ting the internal state of the vector, for example.<br><br>I see no reason =
for a "range" to be applied here. This is best done as a speciali=
zed algorithm, set as a member function of `vector`. It would have versions=
to repeatedly call the given function (`generate_n`) or extract elements f=
rom a range (`copy`). But they would explicitly allocate the range, and any=
modifications to the vector made by the range would result in undefined be=
havior.<br><br>I think that's much better than defining some kind of ou=
tput range type for this.<span class=3D"HOEnZb"><font color=3D"#888888"><br=
></font></span></div></div><span class=3D"HOEnZb"><font color=3D"#888888">
<p></p>
-- <br>
<br>
--- <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" target=3D"_=
blank">std-proposals+unsubscribe@isocpp.org</a>.<br>
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org" target=3D"_blank">std-proposals@isocpp.org</a>.<br>
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/" target=3D"_blank">http://groups.google.com/a/isocpp.org/gro=
up/std-proposals/</a>.<br>
</font></span></blockquote></div><br></div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
--047d7b3a960a4ee233052372cb6d--
.
Author: Nicol Bolas <jmckesson@gmail.com>
Date: Sat, 31 Oct 2015 21:18:43 -0700 (PDT)
Raw View
------=_Part_2288_1748487413.1446351523920
Content-Type: multipart/alternative;
boundary="----=_Part_2289_1520814233.1446351523920"
------=_Part_2289_1520814233.1446351523920
Content-Type: text/plain; charset=UTF-8
On Sunday, November 1, 2015 at 12:07:09 AM UTC-4, Brent Friedman wrote:
>
> Considering the fact that they're not doing the same work, that proves
>> nothing. The "reserve + placement new" is not updating the internal state
>> of the vector, for example.
>
> What internal state is it not updating? The "end" pointer does not require
> 200 assembly instructions to set.
>
I didn't say how much updating the end pointer would take. My point is that
your code is not doing it. And therefore, they are not ending up in the
same place.
I'm not saying your code isn't faster. I'm saying that your test is unfair.
You should revise it to make it more fair, so that the two are clearly
doing the same work.
> And from reading the code, reserve + placement new is hitting the
> important high notes. It's allocating memory, assigning the values, and
> deleting the memory.
>
It's allocating memory, constructing 1000 objects, and deallocating memory.
You forgot to destruct the 1000 objects too.
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
------=_Part_2289_1520814233.1446351523920
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">On Sunday, November 1, 2015 at 12:07:09 AM UTC-4, Brent Fr=
iedman wrote:<blockquote class=3D"gmail_quote" style=3D"margin: 0;margin-le=
ft: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;"><div dir=3D"ltr">=
<blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-=
left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;p=
adding-left:1ex"><span style=3D"font-size:12.8px">Considering the fact that=
they're not doing the same work, that proves nothing. The "reserv=
e + placement new" is not updating the internal state of the vector, f=
or example.</span></blockquote><div>What internal state is it not updating?=
The "end" pointer does not require 200 assembly instructions to =
set.</div></div></blockquote><div><br>I didn't say how much updating th=
e end pointer would take. My point is that your code is not doing it. And t=
herefore, they are not ending up in the same place.<br><br>I'm not sayi=
ng your code isn't faster. I'm saying that your test is unfair. You=
should revise it to make it more fair, so that the two are clearly doing t=
he same work.<br>=C2=A0</div><blockquote class=3D"gmail_quote" style=3D"mar=
gin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;"><=
div dir=3D"ltr"><div> And from reading the code, reserve + placement new is=
hitting the important high notes. It's allocating memory, assigning th=
e values, and deleting the memory.</div></div></blockquote><div><br>It'=
s allocating memory, constructing 1000 objects, and deallocating memory.<br=
><br>You forgot to destruct the 1000 objects too.<br></div></div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
------=_Part_2289_1520814233.1446351523920--
------=_Part_2288_1748487413.1446351523920--
.
Author: Brent Friedman <fourthgeek@gmail.com>
Date: Sat, 31 Oct 2015 23:22:33 -0500
Raw View
--089e015374ec81aeab05237302f5
Content-Type: text/plain; charset=UTF-8
I agree that this test isn't 100% perfect; it wasn't intended to be. I do
think it will prove to be representative.
On Sat, Oct 31, 2015 at 11:18 PM, Nicol Bolas <jmckesson@gmail.com> wrote:
> On Sunday, November 1, 2015 at 12:07:09 AM UTC-4, Brent Friedman wrote:
>>
>> Considering the fact that they're not doing the same work, that proves
>>> nothing. The "reserve + placement new" is not updating the internal state
>>> of the vector, for example.
>>
>> What internal state is it not updating? The "end" pointer does not
>> require 200 assembly instructions to set.
>>
>
> I didn't say how much updating the end pointer would take. My point is
> that your code is not doing it. And therefore, they are not ending up in
> the same place.
>
> I'm not saying your code isn't faster. I'm saying that your test is
> unfair. You should revise it to make it more fair, so that the two are
> clearly doing the same work.
>
>
>> And from reading the code, reserve + placement new is hitting the
>> important high notes. It's allocating memory, assigning the values, and
>> deleting the memory.
>>
>
> It's allocating memory, constructing 1000 objects, and deallocating memory.
>
> You forgot to destruct the 1000 objects too.
>
> --
>
> ---
> 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.
> Visit this group at
> http://groups.google.com/a/isocpp.org/group/std-proposals/.
>
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
--089e015374ec81aeab05237302f5
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">I agree that this test isn't 100% perfect; it wasn'=
;t intended to be. I do think it will prove to be representative.</div><div=
class=3D"gmail_extra"><br><div class=3D"gmail_quote">On Sat, Oct 31, 2015 =
at 11:18 PM, Nicol Bolas <span dir=3D"ltr"><<a href=3D"mailto:jmckesson@=
gmail.com" target=3D"_blank">jmckesson@gmail.com</a>></span> wrote:<br><=
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 class=3D"">On Sunday, =
November 1, 2015 at 12:07:09 AM UTC-4, Brent Friedman wrote:<blockquote cla=
ss=3D"gmail_quote" style=3D"margin:0;margin-left:0.8ex;border-left:1px #ccc=
solid;padding-left:1ex"><div dir=3D"ltr"><blockquote class=3D"gmail_quote"=
style=3D"margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:=
rgb(204,204,204);border-left-style:solid;padding-left:1ex"><span style=3D"f=
ont-size:12.8px">Considering the fact that they're not doing the same w=
ork, that proves nothing. The "reserve + placement new" is not up=
dating the internal state of the vector, for example.</span></blockquote><d=
iv>What internal state is it not updating? The "end" pointer does=
not require 200 assembly instructions to set.</div></div></blockquote></sp=
an><div><br>I didn't say how much updating the end pointer would take. =
My point is that your code is not doing it. And therefore, they are not end=
ing up in the same place.<br><br>I'm not saying your code isn't fas=
ter. I'm saying that your test is unfair. You should revise it to make =
it more fair, so that the two are clearly doing the same work.<br>=C2=A0</d=
iv><span class=3D""><blockquote class=3D"gmail_quote" style=3D"margin:0;mar=
gin-left:0.8ex;border-left:1px #ccc solid;padding-left:1ex"><div dir=3D"ltr=
"><div> And from reading the code, reserve + placement new is hitting the i=
mportant high notes. It's allocating memory, assigning the values, and =
deleting the memory.</div></div></blockquote></span><div><br>It's alloc=
ating memory, constructing 1000 objects, and deallocating memory.<br><br>Yo=
u forgot to destruct the 1000 objects too.<br></div></div><div class=3D"HOE=
nZb"><div class=3D"h5">
<p></p>
-- <br>
<br>
--- <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" target=3D"_=
blank">std-proposals+unsubscribe@isocpp.org</a>.<br>
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org" target=3D"_blank">std-proposals@isocpp.org</a>.<br>
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/" target=3D"_blank">http://groups.google.com/a/isocpp.org/gro=
up/std-proposals/</a>.<br>
</div></div></blockquote></div><br></div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
--089e015374ec81aeab05237302f5--
.
Author: Thiago Macieira <thiago@macieira.org>
Date: Sat, 31 Oct 2015 23:15:03 -0700
Raw View
On Saturday 31 October 2015 23:22:33 Brent Friedman wrote:
> I agree that this test isn't 100% perfect; it wasn't intended to be. I do
> think it will prove to be representative.
Make sure your version works if an exception is thrown in the middle of
constructing the n-th object.
--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
Software Architect - Intel Open Source Technology Center
PGP/GPG: 0x6EF45358; fingerprint:
E067 918B B660 DBD1 105C 966C 33F5 F005 6EF4 5358
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
.
Author: Nicol Bolas <jmckesson@gmail.com>
Date: Sun, 1 Nov 2015 06:10:17 -0800 (PST)
Raw View
------=_Part_2716_2034553587.1446387017723
Content-Type: multipart/alternative;
boundary="----=_Part_2717_1879237400.1446387017723"
------=_Part_2717_1879237400.1446387017723
Content-Type: text/plain; charset=UTF-8
On Sunday, November 1, 2015 at 12:22:38 AM UTC-4, Brent Friedman wrote:
>
> I agree that this test isn't 100% perfect; it wasn't intended to be. I do
> think it will prove to be representative.
>
How can you prove it to be representative when it's not representative?
The only functional difference between the kind of loop you want and the
traditional way is that the traditional way has to check the capacity each
time and potentially reallocate. Your test is *supposed* to measure the
difference between them, to determine how much performance you save when
the insertion operation knows that it won't be reallocating.
But it doesn't measure that. Because your code is different in (several)
other ways, your code cannot measure just that difference. It measures all
of the differences.
Without a valid comparison, what evidence do you have to prove that what
you've shown would be "representative?"
Oh, and a couple of other things.
First, you focus on `push_back` done in a loop. That's fine but... what
about `insert`? That is, if we augment the containers with range TS support:
vec.insert(vec.end(), generator_n_range(100, [&](int) {return get();}));
A `generator_n_range` is a sized range. This means `insert` can query the
size, increase the capacity appropriately, then iterate through the range,
without all that checking to see if the vector needs to be expanded.
In other words, it does exactly what you want. And a bunch of things you
didn't necessarily want but are still useful (namely, being able to insert
arbitrarily into a vector, with only one allocation at most). Things which
your proposal *cannot* do.
So why should we add your thing when we're going to get something that's
fundamentally better?
Second, I noticed when I took your code to GCC 5.2 on that website, the
`vector` version compiled to slightly more than 100 instructions. I find it
interesting that you specifically linked to the Clang version, which showed
a much larger disparity.
That makes it look like you're trying to deliberately stack the deck.
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
------=_Part_2717_1879237400.1446387017723
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr">On Sunday, November 1, 2015 at 12:22:38 AM UTC-4, Brent Fr=
iedman wrote:<blockquote class=3D"gmail_quote" style=3D"margin: 0;margin-le=
ft: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;"><div dir=3D"ltr">=
I agree that this test isn't 100% perfect; it wasn't intended to be=
.. I do think it will prove to be representative.</div></blockquote><div><br=
>How can you prove it to be representative when it's not representative=
?<br><br>The only functional difference between the kind of loop you want a=
nd the traditional way is that the traditional way has to check the capacit=
y each time and potentially reallocate. Your test is <i>supposed</i> to mea=
sure the difference between them, to determine how much performance you sav=
e when the insertion operation knows that it won't be reallocating.<br>=
<br>But it doesn't measure that. Because your code is different in (sev=
eral) other ways, your code cannot measure just that difference. It measure=
s all of the differences.<br><br>Without a valid comparison, what evidence =
do you have to prove that what you've shown would be "representati=
ve?"<br><br>Oh, and a couple of other things.<br><br>First, you focus =
on `push_back` done in a loop. That's fine but... what about `insert`? =
That is, if we augment the containers with range TS support:<br><br><div cl=
ass=3D"prettyprint" style=3D"background-color: rgb(250, 250, 250); border-c=
olor: rgb(187, 187, 187); border-style: solid; border-width: 1px; word-wrap=
: break-word;"><code class=3D"prettyprint"><div class=3D"subprettyprint"><s=
pan style=3D"color: #000;" class=3D"styled-by-prettify">vec</span><span sty=
le=3D"color: #660;" class=3D"styled-by-prettify">.</span><span style=3D"col=
or: #000;" class=3D"styled-by-prettify">insert</span><span style=3D"color: =
#660;" class=3D"styled-by-prettify">(</span><span style=3D"color: #000;" cl=
ass=3D"styled-by-prettify">vec</span><span style=3D"color: #660;" class=3D"=
styled-by-prettify">.</span><span style=3D"color: #008;" class=3D"styled-by=
-prettify">end</span><span style=3D"color: #660;" class=3D"styled-by-pretti=
fy">(),</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> ge=
nerator_n_range</span><span style=3D"color: #660;" class=3D"styled-by-prett=
ify">(</span><span style=3D"color: #066;" class=3D"styled-by-prettify">100<=
/span><span style=3D"color: #660;" class=3D"styled-by-prettify">,</span><sp=
an style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">[&](</span><span style=
=3D"color: #008;" class=3D"styled-by-prettify">int</span><span style=3D"col=
or: #660;" class=3D"styled-by-prettify">)</span><span style=3D"color: #000;=
" class=3D"styled-by-prettify"> </span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">{</span><span style=3D"color: #008;" class=3D"style=
d-by-prettify">return</span><span style=3D"color: #000;" class=3D"styled-by=
-prettify"> </span><span style=3D"color: #008;" class=3D"styled-by-prettify=
">get</span><span style=3D"color: #660;" class=3D"styled-by-prettify">();})=
);</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br></sp=
an></div></code></div><br>A `generator_n_range` is a sized range. This mean=
s `insert` can query the size, increase the capacity appropriately, then it=
erate through the range, without all that checking to see if the vector nee=
ds to be expanded.<br><br>In other words, it does exactly what you want. An=
d a bunch of things you didn't necessarily want but are still useful (n=
amely, being able to insert arbitrarily into a vector, with only one alloca=
tion at most). Things which your proposal <i>cannot</i> do.<br><br>So why s=
hould we add your thing when we're going to get something that's fu=
ndamentally better?<br><br>Second, I noticed when I took your code to GCC 5=
..2 on that website, the `vector` version compiled to slightly more than 100=
instructions. I find it interesting that you specifically linked to the Cl=
ang version, which showed a much larger disparity.<br><br>That makes it loo=
k like you're trying to deliberately stack the deck.<br></div></div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
------=_Part_2717_1879237400.1446387017723--
------=_Part_2716_2034553587.1446387017723--
.
Author: Brent Friedman <fourthgeek@gmail.com>
Date: Sun, 1 Nov 2015 09:06:19 -0600
Raw View
--001a113cacf2c5598705237c0087
Content-Type: text/plain; charset=UTF-8
>
> How can you prove it to be representative when it's not representative?
I find it interesting that you specifically linked to the Clang version,
> which showed a much larger disparity. That makes it look like you're
> trying to deliberately stack the deck.
I am, for example, using the platform-specific knowledge that the
destructor of int is a no-op on the target platform. As I have acknowledged
on several occasions this test is not a full implementation. All of the
hard sciences are allowed to present hypotheses built on imperfect evidence
until better evidence comes forward. This is how science advances.
Reimplementing vector is a lot of work which is why I tried to provide a
partial implementation based on the public interface of vector. I haven't
written a proposal and strong-armed the committee into shoving this into
the standard with no evidence. All I've done is implement a feature in my
code and share some information on a mailing list seeking feedback. I don't
fully understand your attribution of malicious intent. I defaulted to clang
because one of my target platforms requires clang.
> A `generator_n_range` is a sized range. This means `insert` can query the
> size, increase the capacity appropriately, then iterate through the range,
> without all that checking to see if the vector needs to be expanded.
I think this is also a reasonable approach, though it does require more
machinery. You need a range for each technique rather than reusing the
existing algorithms. Eg, transform_n_range, copy_n_range, move_n_range.
Your approach certainly has a better shot of achieving a higher standard of
exception safety since the algorithm stays in the container for its
duration.
Make sure your version works if an exception is thrown in the middle
of constructing
> the n-th object.
The biggest flaw with my approach, I think, is related to this and occurs
independently of exceptions. If you allocate storage with accomodate_back
and then call vector's destructor without constructing those objects then
you will have UB. That occurs whether an exception is thrown or whether you
use accomodate_back and throw away the result range. Our code doesn't
support exceptions so it's not typically the first thing on my mind.
In Nicol's insert via range approach, the container would presumably grow,
then start constructing elements. If a constructor throws, we first need to
destroy those elements and then figure out how to get the vector back into
a valid state. Shrinking the vector back to its old size is probably a bad
idea as if we are out of memory then that is likely to fail. If we try
moving elements down in order to restore the container then one of those
move operations might throw in which case I think we are unrecoverable.
It seems like the only way to have good exception safety here is that if a
bulk insertion operation throws then the entire container gets emptied.
On Sun, Nov 1, 2015 at 8:10 AM, Nicol Bolas <jmckesson@gmail.com> wrote:
> On Sunday, November 1, 2015 at 12:22:38 AM UTC-4, Brent Friedman wrote:
>>
>> I agree that this test isn't 100% perfect; it wasn't intended to be. I do
>> think it will prove to be representative.
>>
>
> How can you prove it to be representative when it's not representative?
>
> The only functional difference between the kind of loop you want and the
> traditional way is that the traditional way has to check the capacity each
> time and potentially reallocate. Your test is *supposed* to measure the
> difference between them, to determine how much performance you save when
> the insertion operation knows that it won't be reallocating.
>
> But it doesn't measure that. Because your code is different in (several)
> other ways, your code cannot measure just that difference. It measures all
> of the differences.
>
> Without a valid comparison, what evidence do you have to prove that what
> you've shown would be "representative?"
>
> Oh, and a couple of other things.
>
> First, you focus on `push_back` done in a loop. That's fine but... what
> about `insert`? That is, if we augment the containers with range TS support:
>
> vec.insert(vec.end(), generator_n_range(100, [&](int) {return get();}));
>
> A `generator_n_range` is a sized range. This means `insert` can query the
> size, increase the capacity appropriately, then iterate through the range,
> without all that checking to see if the vector needs to be expanded.
>
> In other words, it does exactly what you want. And a bunch of things you
> didn't necessarily want but are still useful (namely, being able to insert
> arbitrarily into a vector, with only one allocation at most). Things which
> your proposal *cannot* do.
>
> So why should we add your thing when we're going to get something that's
> fundamentally better?
>
> Second, I noticed when I took your code to GCC 5.2 on that website, the
> `vector` version compiled to slightly more than 100 instructions. I find it
> interesting that you specifically linked to the Clang version, which showed
> a much larger disparity.
>
> That makes it look like you're trying to deliberately stack the deck.
>
> --
>
> ---
> 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.
> Visit this group at
> http://groups.google.com/a/isocpp.org/group/std-proposals/.
>
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
--001a113cacf2c5598705237c0087
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr"><blockquote class=3D"gmail_quote" style=3D"margin:0px 0px =
0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-l=
eft-style:solid;padding-left:1ex"><span style=3D"font-size:12.8px">How can =
you prove it to be representative when it's not representative?</span><=
/blockquote><div><br></div><blockquote class=3D"gmail_quote" style=3D"margi=
n:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204=
);border-left-style:solid;padding-left:1ex"><span style=3D"font-size:12.8px=
">I find it interesting that you specifically linked to the Clang version, =
which showed a much larger disparity.=C2=A0</span><span style=3D"font-size:=
12.8px">That makes it look like you're trying to deliberately stack the=
deck.</span>=C2=A0</blockquote><div><br></div><div>I am, for example, usin=
g the platform-specific knowledge that the destructor of int is a no-op on =
the target platform. As I have acknowledged on several occasions this test =
is not a full implementation. All of the hard sciences are allowed to prese=
nt hypotheses built on imperfect evidence until better evidence comes forwa=
rd. This is how science advances. Reimplementing vector is a lot of work wh=
ich is why I tried to provide a partial implementation based on the public =
interface of vector. I haven't written a proposal and strong-armed the =
committee into shoving this into the standard with no evidence. All I'v=
e done is implement a feature in my code and share some information on a ma=
iling list seeking feedback. I don't fully understand your attribution =
of malicious intent. I defaulted to clang because one of my target platform=
s requires clang.</div><div>=C2=A0</div><blockquote class=3D"gmail_quote" s=
tyle=3D"margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rg=
b(204,204,204);border-left-style:solid;padding-left:1ex"><span style=3D"fon=
t-size:12.8px">A `generator_n_range` is a sized range. This means `insert` =
can query the size, increase the capacity appropriately, then iterate throu=
gh the range, without all that checking to see if the vector needs to be ex=
panded.</span></blockquote><div><br></div><div>I think this is also a reaso=
nable approach, though it does require more machinery. You need a range for=
each technique rather than reusing the existing algorithms. Eg, transform_=
n_range, copy_n_range, move_n_range. Your approach certainly has a better s=
hot of achieving a higher standard of exception safety since the algorithm =
stays in the container for its duration.</div><div><br></div><blockquote cl=
ass=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left-width:1px=
;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1e=
x">=C2=A0<span style=3D"font-size:12.8px">Make sure your version works if a=
n exception is thrown in the middle of=C2=A0</span><span style=3D"font-size=
:12.8px">constructing the n-th object.</span></blockquote><div>The biggest =
flaw with my approach, I think, is related to this and occurs independently=
of exceptions. If you allocate storage with accomodate_back and then call =
vector's destructor without constructing those objects then you will ha=
ve UB. That occurs whether an exception is thrown or whether you use accomo=
date_back and throw away the result range. Our code doesn't support exc=
eptions so it's not typically the first thing on my mind.</div><div><br=
></div><div>In Nicol's insert via range approach, the container would p=
resumably grow, then start constructing elements. If a constructor throws, =
we first need to destroy those elements and then figure out how to get the =
vector back into a valid state. Shrinking the vector back to its old size i=
s probably a bad idea as if we are out of memory then that is likely to fai=
l. If we try moving elements down in order to restore the container then on=
e of those move operations might throw in which case I think we are unrecov=
erable.</div><div><br></div><div>It seems like the only way to have good ex=
ception safety here is that if a bulk insertion operation throws then the e=
ntire container gets emptied.</div></div><div class=3D"gmail_extra"><br><di=
v class=3D"gmail_quote">On Sun, Nov 1, 2015 at 8:10 AM, Nicol Bolas <span d=
ir=3D"ltr"><<a href=3D"mailto:jmckesson@gmail.com" target=3D"_blank">jmc=
kesson@gmail.com</a>></span> wrote:<br><blockquote class=3D"gmail_quote"=
style=3D"margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><d=
iv dir=3D"ltr"><span class=3D"">On Sunday, November 1, 2015 at 12:22:38 AM =
UTC-4, Brent Friedman wrote:<blockquote class=3D"gmail_quote" style=3D"marg=
in:0;margin-left:0.8ex;border-left:1px #ccc solid;padding-left:1ex"><div di=
r=3D"ltr">I agree that this test isn't 100% perfect; it wasn't inte=
nded to be. I do think it will prove to be representative.</div></blockquot=
e></span><div><br>How can you prove it to be representative when it's n=
ot representative?<br><br>The only functional difference between the kind o=
f loop you want and the traditional way is that the traditional way has to =
check the capacity each time and potentially reallocate. Your test is <i>su=
pposed</i> to measure the difference between them, to determine how much pe=
rformance you save when the insertion operation knows that it won't be =
reallocating.<br><br>But it doesn't measure that. Because your code is =
different in (several) other ways, your code cannot measure just that diffe=
rence. It measures all of the differences.<br><br>Without a valid compariso=
n, what evidence do you have to prove that what you've shown would be &=
quot;representative?"<br><br>Oh, and a couple of other things.<br><br>=
First, you focus on `push_back` done in a loop. That's fine but... what=
about `insert`? That is, if we augment the containers with range TS suppor=
t:<br><br><div style=3D"background-color:rgb(250,250,250);border-color:rgb(=
187,187,187);border-style:solid;border-width:1px;word-wrap:break-word"><cod=
e><div><span style=3D"color:#000">vec</span><span style=3D"color:#660">.</s=
pan><span style=3D"color:#000">insert</span><span style=3D"color:#660">(</s=
pan><span style=3D"color:#000">vec</span><span style=3D"color:#660">.</span=
><span style=3D"color:#008">end</span><span style=3D"color:#660">(),</span>=
<span style=3D"color:#000"> generator_n_range</span><span style=3D"color:#6=
60">(</span><span style=3D"color:#066">100</span><span style=3D"color:#660"=
>,</span><span style=3D"color:#000"> </span><span style=3D"color:#660">[&am=
p;](</span><span style=3D"color:#008">int</span><span style=3D"color:#660">=
)</span><span style=3D"color:#000"> </span><span style=3D"color:#660">{</sp=
an><span style=3D"color:#008">return</span><span style=3D"color:#000"> </sp=
an><span style=3D"color:#008">get</span><span style=3D"color:#660">();}));<=
/span><span style=3D"color:#000"><br></span></div></code></div><br>A `gener=
ator_n_range` is a sized range. This means `insert` can query the size, inc=
rease the capacity appropriately, then iterate through the range, without a=
ll that checking to see if the vector needs to be expanded.<br><br>In other=
words, it does exactly what you want. And a bunch of things you didn't=
necessarily want but are still useful (namely, being able to insert arbitr=
arily into a vector, with only one allocation at most). Things which your p=
roposal <i>cannot</i> do.<br><br>So why should we add your thing when we=
9;re going to get something that's fundamentally better?<br><br>Second,=
I noticed when I took your code to GCC 5.2 on that website, the `vector` v=
ersion compiled to slightly more than 100 instructions. I find it interesti=
ng that you specifically linked to the Clang version, which showed a much l=
arger disparity.<br><br>That makes it look like you're trying to delibe=
rately stack the deck.<br></div></div><div class=3D"HOEnZb"><div class=3D"h=
5">
<p></p>
-- <br>
<br>
--- <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" target=3D"_=
blank">std-proposals+unsubscribe@isocpp.org</a>.<br>
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org" target=3D"_blank">std-proposals@isocpp.org</a>.<br>
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/" target=3D"_blank">http://groups.google.com/a/isocpp.org/gro=
up/std-proposals/</a>.<br>
</div></div></blockquote></div><br></div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
--001a113cacf2c5598705237c0087--
.
Author: Nicol Bolas <jmckesson@gmail.com>
Date: Sun, 1 Nov 2015 09:16:51 -0800 (PST)
Raw View
------=_Part_2901_812395746.1446398211488
Content-Type: multipart/alternative;
boundary="----=_Part_2902_724001785.1446398211489"
------=_Part_2902_724001785.1446398211489
Content-Type: text/plain; charset=UTF-8
On Sunday, November 1, 2015 at 10:06:22 AM UTC-5, Brent Friedman wrote:
>
> How can you prove it to be representative when it's not representative?
>
>
> I find it interesting that you specifically linked to the Clang version,
>> which showed a much larger disparity. That makes it look like you're
>> trying to deliberately stack the deck.
>
>
> I am, for example, using the platform-specific knowledge that the
> destructor of int is a no-op on the target platform. As I have acknowledged
> on several occasions this test is not a full implementation. All of the
> hard sciences are allowed to present hypotheses built on imperfect evidence
> until better evidence comes forward. This is how science advances.
>
That's only half true. Sure, you're allowed to "present" hypotheses based
on incomplete evidence. But that will not stop your fellow scientists from
pointing out your incomplete evidence. Also, while you can present such
hypotheses, they're not likely to become accepted *until* more compelling
evidence shows up. Thus, you're always encouraged to present the most
complete evidence you can.
Also, if your incomplete evidence could be made complete by you taking 20
more minutes to improve your experiment, your fellow scientists aren't
exactly going to look very fondly on your evidence. Indeed, that probably
wouldn't even pass peer review.
> Reimplementing vector is a lot of work which is why I tried to provide a
> partial implementation based on the public interface of vector. I haven't
> written a proposal and strong-armed the committee into shoving this into
> the standard with no evidence. All I've done is implement a feature in my
> code and share some information on a mailing list seeking feedback. I don't
> fully understand your attribution of malicious intent. I defaulted to clang
> because one of my target platforms requires clang.
>
I'm not asking you to reimplement vector (even though a basic
reimplementation of the key points is really not that hard. It's not like
you have to use allocators and such. You probably spent more time writing
responses in this thread). I'm asking you to make an apples-to-apples
comparison where the only difference is the part that actually matters.
My attribution of maliciousness was due to the fact that it would have been
trivial for you to test GCC as well. More complete data makes for more
compelling evidence, so I assumed you did. It was just a button click,
after all. But there is a saying about attributing to malice
<https://en.wikipedia.org/wiki/Hanlon's_razor>... ;)
A `generator_n_range` is a sized range. This means `insert` can query the
>> size, increase the capacity appropriately, then iterate through the range,
>> without all that checking to see if the vector needs to be expanded.
>
>
> I think this is also a reasonable approach, though it does require more
> machinery. You need a range for each technique rather than reusing the
> existing algorithms. Eg, transform_n_range, copy_n_range, move_n_range.
>
You don't need an `n_range` function to have a countable range. You simply
need a *countable range*. Vector provides a countable range. As does deque.
As does any container that provides random access iterators (string, array,
etc).
Transform is something that takes input, specifically a range. A transform
adapter will transform each element in the range to some output item.
That's its job. If the input range is countable, then transform adapter's
range will also be countable, since it can't remove or insert elements. So
you don't need a `transform_n_range` at all; just use the transform adapter
on your range. So if you do apply transform to a vector and then `insert`
that range into another vector, then the destination vector can increase
the capacity based on the combined range's size once.
Also, `copy_n_range` makes no sense. That's *what `vector::insert` does*;
it copies the elements from a range into the vector. And if you mean to
copy a single item N times, that is *also what `vector::insert` does
<http://en.cppreference.com/w/cpp/container/vector/insert>*. Moving a range
simply requires the ability to create a moveable range. Which again, the
ranges TS will provide for basic usability's sake. If the input range was
countable, the adapted moveable range too should be countable.
`generate_n` is needed to get a countable generation range, because the
generation function has no state outside of what it brings with it. The
range is simply "call this function X times", so you need an X to know how
many times to call it.
So no, you simply need to have a countable range, not a bunch of "n_range"
functions.
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
------=_Part_2902_724001785.1446398211489
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
On Sunday, November 1, 2015 at 10:06:22 AM UTC-5, Brent Friedman wrote:<blo=
ckquote class=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-=
left: 1px #ccc solid;padding-left: 1ex;"><div dir=3D"ltr"><blockquote class=
=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left-width:1px;bo=
rder-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">=
<span style=3D"font-size:12.8px">How can you prove it to be representative =
when it's not representative?</span></blockquote><div><br></div><blockq=
uote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left-wi=
dth:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-=
left:1ex"><span style=3D"font-size:12.8px">I find it interesting that you s=
pecifically linked to the Clang version, which showed a much larger dispari=
ty.=C2=A0</span><span style=3D"font-size:12.8px">That makes it look like yo=
u're trying to deliberately stack the deck.</span>=C2=A0</blockquote><d=
iv><br></div><div>I am, for example, using the platform-specific knowledge =
that the destructor of int is a no-op on the target platform. As I have ack=
nowledged on several occasions this test is not a full implementation. All =
of the hard sciences are allowed to present hypotheses built on imperfect e=
vidence until better evidence comes forward. This is how science advances.<=
/div></div></blockquote><div><br>That's only half true. Sure, you'r=
e allowed to "present" hypotheses based on incomplete evidence. B=
ut that will not stop your fellow scientists from pointing out your incompl=
ete evidence. Also, while you can present such hypotheses, they're not =
likely to become accepted <i>until</i> more compelling evidence shows up. T=
hus, you're always encouraged to present the most complete evidence you=
can.<br><br>Also, if your incomplete evidence could be made complete by yo=
u taking 20 more minutes to improve your experiment, your fellow scientists=
aren't exactly going to look very fondly on your evidence. Indeed, tha=
t probably wouldn't even pass peer review.<br>=C2=A0</div><blockquote c=
lass=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-left: 1px=
#ccc solid;padding-left: 1ex;"><div dir=3D"ltr"><div>Reimplementing vector=
is a lot of work which is why I tried to provide a partial implementation =
based on the public interface of vector. I haven't written a proposal a=
nd strong-armed the committee into shoving this into the standard with no e=
vidence. All I've done is implement a feature in my code and share some=
information on a mailing list seeking feedback. I don't fully understa=
nd your attribution of malicious intent. I defaulted to clang because one o=
f my target platforms requires clang.</div></div></blockquote><div><br>I=
9;m not asking you to reimplement vector (even though a basic reimplementat=
ion of the key points is really not that hard. It's not like you have t=
o use allocators and such. You probably spent more time writing responses i=
n this thread). I'm asking you to make an apples-to-apples comparison w=
here the only difference is the part that actually matters.<br><br>My attri=
bution of maliciousness was due to the fact that it would have been trivial=
for you to test GCC as well. More complete data makes for more compelling =
evidence, so I assumed you did. It was just a button click, after all. But =
there is a saying about <a href=3D"https://en.wikipedia.org/wiki/Hanlon'=
;s_razor">attributing to malice</a>... ;)<br><br></div><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></div><blockquote class=3D"g=
mail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left-width:1px;border-=
left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><span=
style=3D"font-size:12.8px">A `generator_n_range` is a sized range. This me=
ans `insert` can query the size, increase the capacity appropriately, then =
iterate through the range, without all that checking to see if the vector n=
eeds to be expanded.</span></blockquote><div><br></div><div>I think this is=
also a reasonable approach, though it does require more machinery. You nee=
d a range for each technique rather than reusing the existing algorithms. E=
g, transform_n_range, copy_n_range, move_n_range.</div></div></blockquote><=
div><br>You don't need an `n_range` function to have a countable range.=
You simply need a <i>countable range</i>. Vector provides a countable rang=
e. As does deque. As does any container that provides random access iterato=
rs (string, array, etc).<br><br>Transform is something that takes input, sp=
ecifically a range. A transform adapter will transform each element in the =
range to some output item. That's its job. If the input range is counta=
ble, then transform adapter's range will also be countable, since it ca=
n't remove or insert elements. So you don't need a `transform_n_ran=
ge` at all; just use the transform adapter on your range. So if you do appl=
y transform to a vector and then `insert` that range into another vector, t=
hen the destination vector can increase the capacity based on the combined =
range's size once.<br><br>Also, `copy_n_range` makes no sense. That'=
;s <i>what `vector::insert` does</i>; it copies the elements from a range i=
nto the vector. And if you mean to copy a single item N times, that is <i>a=
lso <a href=3D"http://en.cppreference.com/w/cpp/container/vector/insert">wh=
at `vector::insert` does</a></i>. Moving a range simply requires the abilit=
y to create a moveable range. Which again, the ranges TS will provide for b=
asic usability's sake. If the input range was countable, the adapted mo=
veable range too should be countable.<br><br> `generate_n` is needed to get=
a countable generation range, because the
generation function has no state outside of what it brings with it. The
range is simply "call this function X times", so you need an X t=
o know=20
how many times to call it.<br><br>So no, you simply need to have a countabl=
e range, not a bunch of "n_range" functions.<br></div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
------=_Part_2902_724001785.1446398211489--
------=_Part_2901_812395746.1446398211488--
.
Author: Casey Carter <cartec69@gmail.com>
Date: Sun, 1 Nov 2015 09:22:58 -0800 (PST)
Raw View
------=_Part_57_1222475777.1446398579103
Content-Type: multipart/alternative;
boundary="----=_Part_58_1044695853.1446398579104"
------=_Part_58_1044695853.1446398579104
Content-Type: text/plain; charset=UTF-8
On Sunday, November 1, 2015 at 9:06:22 AM UTC-6, Brent Friedman wrote:
>
> In Nicol's insert via range approach, the container would presumably grow,
>> then start constructing elements. If a constructor throws, we first need to
>> destroy those elements and then figure out how to get the vector back into
>> a valid state. Shrinking the vector back to its old size is probably a bad
>> idea as if we are out of memory then that is likely to fail. If we try
>> moving elements down in order to restore the container then one of those
>> move operations might throw in which case I think we are unrecoverable.
>>
>
>
std::vector already has a similar operation: insert(pos, first, last) which
inserts the range of elements [first, last) into the vector at position pos.
insert(pos, range) would have equivalent semantics, and handle exceptions
in the same way. A quality implementation of std::vector will determine the
size of the input range when possible ([first, last) or range model ForwardRange
or SizedRange), adjust its capacity exactly once, and shift existing
elements into their final positions before performing the insertions in a
fashion that need not check capacity. Since insert only needs to support
the basic exception safety guarantee, clearing the container is a perfectly
valid response to an exception thrown during the insertion. I believe
existing implementations provide stronger guarantees than empty, but I'm
not going to put forth the effort to investigate at this time ;)
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
------=_Part_58_1044695853.1446398579104
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
On Sunday, November 1, 2015 at 9:06:22 AM UTC-6, Brent Friedman wrote:<bloc=
kquote class=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-l=
eft: 1px #ccc solid;padding-left: 1ex;"><div dir=3D"ltr"><blockquote class=
=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left-width:1px;bo=
rder-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">=
In Nicol's insert via range approach, the container would presumably gr=
ow, then start constructing elements. If a constructor throws, we first nee=
d to destroy those elements and then figure out how to get the vector back =
into a valid state. Shrinking the vector back to its old size is probably a=
bad idea as if we are out of memory then that is likely to fail. If we try=
moving elements down in order to restore the container then one of those m=
ove operations might throw in which case I think we are unrecoverable.<br><=
/blockquote><div><br></div></div></blockquote><div><br></div><div><font fac=
e=3D"courier new, monospace">std::vector</font> already has a similar opera=
tion: <font face=3D"courier new, monospace">insert(pos, first, last)</font>=
which inserts the range of elements <font face=3D"courier new, monospace">=
[first, last)</font> into the vector at position <font face=3D"courier new,=
monospace">pos</font>. <font face=3D"courier new, monospace">insert(pos, r=
ange)</font> would have equivalent semantics, and handle exceptions in the =
same way. A quality implementation of <font face=3D"courier new, monospace"=
>std::vector</font> will determine the size of the input range when possibl=
e (<font face=3D"courier new, monospace">[first, last)</font> or <font face=
=3D"courier new, monospace">range </font>model <font face=3D"courier new, m=
onospace">ForwardRange </font>or <font face=3D"courier new, monospace">Size=
dRange</font>), adjust its capacity exactly once, and shift existing elemen=
ts into their final positions before performing the insertions in a fashion=
that need not check capacity. Since <font face=3D"courier new, monospace">=
insert</font> only needs to support the basic exception safety guarantee, c=
learing the container is a perfectly valid response to an exception thrown =
during the insertion. I believe existing implementations provide stronger g=
uarantees than empty, but I'm not going to put forth the effort to inve=
stigate at this time ;)</div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
------=_Part_58_1044695853.1446398579104--
------=_Part_57_1222475777.1446398579103--
.
Author: Brent Friedman <fourthgeek@gmail.com>
Date: Sun, 1 Nov 2015 12:29:45 -0600
Raw View
--001a11c2ff944d529505237ed81c
Content-Type: text/plain; charset=UTF-8
>
> std::vector already has a similar operation: insert(pos, first, last)
> which inserts the range of elements [first, last) into the vector at
> position pos
>
And if you mean to copy a single item N times, that is *also what
> `vector::insert` does
> <http://en.cppreference.com/w/cpp/container/vector/insert>*.
Perhaps some of the confusion in this thread has stemmed from my
unfamiliarity with this signature and its implementation. I didn't
completely realize that it could achieve the same ends given the
appropriate adapters.
You don't need an `n_range` function to have a countable range. You simply
> need a *countable range*.
Yep, that's correct. I intended to imply that "transform", "copy", "move"
adapters were needed, not that n-variations on each of them were needed. I
can understand how it would have been interpreted that way however.
But there is a saying about attributing to malice
> <https://en.wikipedia.org/wiki/Hanlon's_razor>... ;)
Definitely applicable in this scenario.
On Sun, Nov 1, 2015 at 11:22 AM, Casey Carter <cartec69@gmail.com> wrote:
> On Sunday, November 1, 2015 at 9:06:22 AM UTC-6, Brent Friedman wrote:
>>
>> In Nicol's insert via range approach, the container would presumably
>>> grow, then start constructing elements. If a constructor throws, we first
>>> need to destroy those elements and then figure out how to get the vector
>>> back into a valid state. Shrinking the vector back to its old size is
>>> probably a bad idea as if we are out of memory then that is likely to fail.
>>> If we try moving elements down in order to restore the container then one
>>> of those move operations might throw in which case I think we are
>>> unrecoverable.
>>>
>>
>>
> std::vector already has a similar operation: insert(pos, first, last)
> which inserts the range of elements [first, last) into the vector at
> position pos. insert(pos, range) would have equivalent semantics, and
> handle exceptions in the same way. A quality implementation of std::vector
> will determine the size of the input range when possible ([first, last)
> or range model ForwardRange or SizedRange), adjust its capacity exactly
> once, and shift existing elements into their final positions before
> performing the insertions in a fashion that need not check capacity. Since
> insert only needs to support the basic exception safety guarantee,
> clearing the container is a perfectly valid response to an exception thrown
> during the insertion. I believe existing implementations provide stronger
> guarantees than empty, but I'm not going to put forth the effort to
> investigate at this time ;)
>
> --
>
> ---
> 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.
> Visit this group at
> http://groups.google.com/a/isocpp.org/group/std-proposals/.
>
--
---
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.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.
--001a11c2ff944d529505237ed81c
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable
<div dir=3D"ltr"><blockquote class=3D"gmail_quote" style=3D"margin:0px 0px =
0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-l=
eft-style:solid;padding-left:1ex">std::vector already has a similar operati=
on: insert(pos, first, last) which inserts the range of elements [first, la=
st) into the vector at position pos<br></blockquote><div><br></div><blockqu=
ote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left-wid=
th:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-l=
eft:1ex"><span style=3D"font-size:12.8px">=C2=A0And if you mean to copy a s=
ingle item N times, that is=C2=A0</span><i style=3D"font-size:12.8px">also=
=C2=A0<a href=3D"http://en.cppreference.com/w/cpp/container/vector/insert" =
target=3D"_blank">what `vector::insert` does</a></i><span style=3D"font-siz=
e:12.8px">.=C2=A0</span>=C2=A0</blockquote><div><br></div><div>Perhaps some=
of the confusion in this thread has stemmed from my unfamiliarity with thi=
s signature and its implementation. I didn't completely realize that it=
could achieve the same ends given the appropriate adapters.</div><div><br>=
</div><blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;b=
order-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:s=
olid;padding-left:1ex"><span style=3D"font-size:12.8px">You don't need =
an `n_range` function to have a countable range. You simply need a=C2=A0</s=
pan><i style=3D"font-size:12.8px">countable range</i><span style=3D"font-si=
ze:12.8px">.=C2=A0</span></blockquote><div>Yep, that's correct. I inten=
ded to imply that "transform", "copy", "move"=
adapters were needed, not that n-variations on each of them were needed. I=
can understand how it would have been interpreted that way however.</div><=
div><br></div><blockquote class=3D"gmail_quote" style=3D"margin:0px 0px 0px=
0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left=
-style:solid;padding-left:1ex"><span style=3D"font-size:12.8px">But there i=
s a saying about=C2=A0</span><a href=3D"https://en.wikipedia.org/wiki/Hanlo=
n's_razor" target=3D"_blank" style=3D"font-size:12.8px">attributing to =
malice</a><span style=3D"font-size:12.8px">... ;)</span></blockquote><div>D=
efinitely applicable in this scenario.</div><div>=C2=A0<br></div></div><div=
class=3D"gmail_extra"><br><div class=3D"gmail_quote">On Sun, Nov 1, 2015 a=
t 11:22 AM, Casey Carter <span dir=3D"ltr"><<a href=3D"mailto:cartec69@g=
mail.com" target=3D"_blank">cartec69@gmail.com</a>></span> wrote:<br><bl=
ockquote class=3D"gmail_quote" style=3D"margin:0 0 0 .8ex;border-left:1px #=
ccc solid;padding-left:1ex"><span class=3D"">On Sunday, November 1, 2015 at=
9:06:22 AM UTC-6, Brent Friedman wrote:<blockquote class=3D"gmail_quote" s=
tyle=3D"margin:0;margin-left:0.8ex;border-left:1px #ccc solid;padding-left:=
1ex"><div dir=3D"ltr"><blockquote class=3D"gmail_quote" style=3D"margin:0px=
0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);bor=
der-left-style:solid;padding-left:1ex">In Nicol's insert via range appr=
oach, the container would presumably grow, then start constructing elements=
.. If a constructor throws, we first need to destroy those elements and then=
figure out how to get the vector back into a valid state. Shrinking the ve=
ctor back to its old size is probably a bad idea as if we are out of memory=
then that is likely to fail. If we try moving elements down in order to re=
store the container then one of those move operations might throw in which =
case I think we are unrecoverable.<br></blockquote><div><br></div></div></b=
lockquote><div><br></div></span><div><font face=3D"courier new, monospace">=
std::vector</font> already has a similar operation: <font face=3D"courier n=
ew, monospace">insert(pos, first, last)</font> which inserts the range of e=
lements <font face=3D"courier new, monospace">[first, last)</font> into the=
vector at position <font face=3D"courier new, monospace">pos</font>. <font=
face=3D"courier new, monospace">insert(pos, range)</font> would have equiv=
alent semantics, and handle exceptions in the same way. A quality implement=
ation of <font face=3D"courier new, monospace">std::vector</font> will dete=
rmine the size of the input range when possible (<font face=3D"courier new,=
monospace">[first, last)</font> or <font face=3D"courier new, monospace">r=
ange </font>model <font face=3D"courier new, monospace">ForwardRange </font=
>or <font face=3D"courier new, monospace">SizedRange</font>), adjust its ca=
pacity exactly once, and shift existing elements into their final positions=
before performing the insertions in a fashion that need not check capacity=
.. Since <font face=3D"courier new, monospace">insert</font> only needs to s=
upport the basic exception safety guarantee, clearing the container is a pe=
rfectly valid response to an exception thrown during the insertion. I belie=
ve existing implementations provide stronger guarantees than empty, but I&#=
39;m not going to put forth the effort to investigate at this time ;)</div>=
<div class=3D"HOEnZb"><div class=3D"h5">
<p></p>
-- <br>
<br>
--- <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" target=3D"_=
blank">std-proposals+unsubscribe@isocpp.org</a>.<br>
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org" target=3D"_blank">std-proposals@isocpp.org</a>.<br>
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/" target=3D"_blank">http://groups.google.com/a/isocpp.org/gro=
up/std-proposals/</a>.<br>
</div></div></blockquote></div><br></div>
<p></p>
-- <br />
<br />
--- <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 />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />
--001a11c2ff944d529505237ed81c--
.