Eric Freeman
Eric Freeman

Reputation: 82

How come the move constructor isnt called in my code?

#include <iostream>
#include<algorithm>

template<class T>
class Matrix {
    std::pair<unsigned int,unsigned int> dim;
    T* elem;
public:
    Matrix(unsigned int d1, unsigned int d2) :
        dim{std::make_pair(d1,d2)}, elem{new T[d1*d2]} { }

    unsigned int size() const { return (dim.first)*(dim.second); }

    Matrix(Matrix&& a){
        std::cout<<"move constructor";
        elem = a.elem;
        a.elem =nullptr;
        dim.first = a.dim.first+7;
        dim.second = a.dim.second;
        a.dim.first=0;
        a.dim.second=0;
    }

    Matrix& operator=(Matrix&& a){
        std::cout<<"move operator=";
        elem = a.elem;
        a.elem =nullptr;
        dim.first = a.dim.first;
        dim.second = a.dim.second;
        a.dim.first=0;
        a.dim.second=0;
        return *this;
    }

    ~Matrix() { delete[] elem; }
};

using namespace std;

int main() {
    Matrix<unsigned int> bob = Matrix<unsigned int>(5,5);
    Matrix<unsigned int> bob2(Matrix<unsigned int>(5,5));
    return 0;
}//no output

I'm expecting it to print "move constructor" and "move operator=" But it prints neither of them.

Matrix(5,5) doesnt have a name so i assume its rvalue, thus im expecting Matrix<unsigned int> bob = Matrix<unsigned int>(5,5); to call the move constructor

Upvotes: 1

Views: 112

Answers (1)

Lightness Races in Orbit
Lightness Races in Orbit

Reputation: 385108

This is a feature.

Moves are better than copies, but C++ in this case is allowed to skip even the move! It's called elision and is most noticeable when you initialise like this, or return from a function. In fact since C++17 I think it's even guaranteed; in the olden days it was just a permitted optimisation. Note that it's permitted even if the constructor has side effects (e.g. output), which is quite unusual for C++.

But there is nothing wrong with your code, which is indeed correctly poised to use the move constructor. The code would not compile otherwise, as elision is only permitted when the move could have been performed.

Upvotes: 6

Related Questions