I had a question, given:
let mut v: Vec<T>; assert_eq!(v.capacity(), v.len()); v.insert(middle, val);
how much memory would be copied around. The vector needs to grow, so it might grow first, copying its whole contents to the new memory, and then do the insert, moving the
[middle, len()) elements one to the right. Alternatively, it might copy
[0, middle) to the new memory first, insert val, then copy
[middle, len()). The difference being, the first approach moves the
[middle, len) elements twice, while the second approach moves them only once.
In C++ this question is trivial to answer: define a
T with a move constructor that increases an internal count on every move, perform the op, print out the count.
I have no idea how to simply answer this question in Rust, or more in general, how to find out where moves / memcpy-s due to move actually happen.
This is particularly worry-some, since in my experience Rust often
memcpys too much memory around all the time. I have to figure this out things before, and the only reliable method I have is… using godbolt to introspect the assembly.
In this case, https://rust.godbolt.org/z/oRJg7V , I need to basically know that what’s happening here is that the vector is first, realloc into new memory (whole vector moved once in the worst case), and then the tail is moved by one to the right (memmove), and then the element is inserted. As opposed to using realloc_in_place, and if that fails, move head, insert, move tail.
I could obviously go ahead and look and the source code, but what I’m looking for is for an easy way to “debug” (or add tests) for performance issues related to unnecessary
memmoves. As in, how
Vec::insert actually works is not the point here, the point is how would I add a test to make sure that it works correctly.