std::vector move assign patch
Jonathan Wakely
jwakely@redhat.com
Tue Apr 25 13:40:00 GMT 2017
On 25/04/17 13:52 +0100, Jonathan Wakely wrote:
>On 24/04/17 22:10 +0200, Marc Glisse wrote:
>>It seems that this patch had 2 consequences that may or may not have
>>been planned. Consider this example (from PR64601)
>>
>>#include <vector>
>>typedef std::vector<int> V;
>>void f(V&v,V&w){ V(std::move(w)).swap(v); }
>>void g(V&v,V&w){ v=std::move(w); }
>>
>>1) We generate shorter code for f than for g, probably since the fix
>>for PR59738. g ends up zeroing v, copying w to v, and finally
>>zeroing w, and for weird reasons (and because we swap the members
>>one by one) the standard prevents us from assuming that v and w do
>>not overlap in weird ways so we cannot optimize as much as one might
>>expect.
>
>f has an additional precondition (that the allocators of the vectors
>being swapped must propagate on swap or be equal) and so the swap code
>doesn't have to worry about non-equal allocators.
>
>g has to be able to cope with the case where the allocator doesn't
>propagate and isn't equal, and so is more complicated.
>
>However, the propagation trait is known at compile-time, and for the
>common case so is the equality condition, so it's unfortunate if that
>can't be simplified (I'm sure you've analysed it carefully already
>though!)
I tried the attached patch, but it doesn't make any difference
(unsurprisingly, because after inlining we know that:
if (__rv.get_allocator() != __m)
is false, so making it a compile-time condition doesn't change
anything).
It might be a nice improvement anyway, as it means the
allocator-extended constructor doesn't require movable types if the
allocators are always equal. It extends the set of types that can be
used with that constructor.
>>2) g(v,v) seems to turn v into a nice empty vector,
>
>Yes.
>
>>while f(v,v) turns it into an invalid vector pointing at released
>>memory.
>
>Does it?! I don't see that happening, and it's a bug if it does.
>
>>Since 2) is a nice side-effect, it may not be worth rewriting
>>operator= in a way that improves 1) but loses 2). Anyway, just
>>mentioning this here.
-------------- next part --------------
A non-text attachment was scrubbed...
Name: patch.txt
Type: text/x-patch
Size: 1969 bytes
Desc: not available
URL: <http://gcc.gnu.org/pipermail/libstdc++/attachments/20170425/5256d421/attachment.bin>
More information about the Libstdc++
mailing list