Home > Net >  Why doesn't move vector trigger moving internal elements?
Why doesn't move vector trigger moving internal elements?

Time:05-18

For the following code, I am confused about p3 vector, why move operators are not triggered for Test? For p1 and p2, I can understand that all the elements need to copied be over.

Does that mean when we move a vector, it modifies the vector object so the elements of the vector will leave untouched. Whereas when we copy a vector, we have to copy every single element. Is there a vector operation where the move operator of an element will be trigger?

#include <iostream>
#include <vector> 

using namespace std;

class Test {
  public: 
    Test(int a) {
        std::cout << " default " << std::endl;
    }
    
    Test(const Test& o) {
        std::cout << " copy ctor " << std::endl;
    }
    
    Test& operator=(const Test& o) {
        std::cout << " copy assign " << std::endl;
        return *this;
    }
    
    Test(Test&& o) {
        std::cout << " move ctor" << std::endl;
    }
    
    Test& operator=(Test&& o) {
        std::cout << " move assign " << std::endl;
        return *this;
    }
};

int main()
{
  std::cout << " p: " << std::endl;
  std::vector<Test> p = {Test(0), Test(0)}; 
  std::cout << std::endl;
   
  std::cout << " vec p1 " << std::endl;
  std::vector<Test> p1 = p;
  std::cout << std::endl;
    
  std::cout << " vec p2 " << std::endl;
  std::vector<Test> p2;
  p2.reserve(2);
  p2.emplace_back(0);
  p2.emplace_back(0);
  std::cout << std::endl;
   
  std::cout << " vec p3 " << std::endl;
  std::vector<Test> p3 = std::move(p);
}

Output:

p: 
default 
default 
copy ctor 
copy ctor 

vec p1 
copy ctor 
copy ctor 

vec p2 
default 
default 

vec p3 

CodePudding user response:

A vector is essentially a pointer to an array. Moving the vector simply swaps the array pointers between the two vectors, the arrays themselves are unchanged.

CodePudding user response:

vector is basically

template <typename T>
class vector
{
    T* data;
    T* end_data;
    T* end_capacity;
public:
    //...
};

When you want to copy that, you need to allocate new space for data to point to and then copy the elements from the source vector into the destination.

When moving this doesn't need to happen. Moving basically empties the source location, which in this case means copying the pointers into the moved to vector and then setting the pointers in the moved from vector to null. This is why moving can be such a performance gain.

  •  Tags:  
  • c
  • Related