This is the mail archive of the mailing list for the libstdc++ project.

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: std::vector move assign patch

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

2) g(v,v) seems to turn v into a nice empty vector,


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.

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]