1

Given these classes:

class Matrix{
//...
public:
   Matrix(int row, int column) {
     ...
   };
   Matrix operator+(const Matrix &matrix) const{
   ...
   }
};
class MatrixSquare : public Matrix{
//...
public:
   MatrixSquare(int size) {
     ...
   };
   MatrixSquare operator+(const MatrixSquare &matrix) const{
     ??????
   }
};

I'm trying to implement MatrixSquare operator+ by using Matrix::operator+. But Matrix::operator+ returns Matrix.

Do I have to create the copy constructor MatrixSquare(const Matrix &matrix) ?

Remy Lebeau
  • 555,201
  • 31
  • 458
  • 770
  • 3
    It's often the case that a Square is not a good fit as a subclass for a more-general Rectangle class; that might be the case here as well (it's hard to say without knowing more about what your classes are for): https://en.wikipedia.org/wiki/Circle-ellipse_problem – Jeremy Friesner Jul 15 '23 at 22:33
  • 1
    Sounds like a MatrixSquare should *contain* a Matrix, but not *be* a Matrix. It doesn't seem (with what little information I have) that a MatrixSquare *is-a* Matrix, because it doesn't seem to pass the Liskov Substitution Principle sniff test. – Eljay Jul 15 '23 at 22:37
  • In addition to `operator+`, provide `operator+=`, and put the actual implementation there. `operator+` can be easily implemented in terms of `+=` (together with a copy constructor), and `+=` can be easily reused by the derived class. – Igor Tandetnik Jul 15 '23 at 22:38

1 Answers1

0

You can use the recurring template pattern and don't need to implement the operator in the child

template <typename Child>
class Matrix {
//...
public:
   Matrix(int row, int column) {
     ...
   }
   Child operator+(const Child &matrix) const {
   ...
   }
};

class MatrixSquare : public Matrix<MatrixSquare> {
//...
public:
   MatrixSquare(int size) : Matrix(size, size) {
     ...
   }
};
273K
  • 29,503
  • 10
  • 41
  • 64
  • And change everything in the rest of the code that uses `Matrix`, a class, to use `Matrix`, a template... – Sam Varshavchik Jul 15 '23 at 22:37
  • It is unnecessary, the matrix sum is a common operation for all kinds of matrices. – 273K Jul 15 '23 at 22:39
  • 2
    I am not talking about the matrix sum, but a few thousand lines of the rest of the code that declares `Matrix a, b;`, for example, then does something with `a` and `b`. What do you propose `a` and `b` be, once `Matrix` becomes a template? – Sam Varshavchik Jul 15 '23 at 22:41
  • 2
    FYI, in C++23, you can use [deducing `this`](https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2021/p0847r7.html) (P0847) to avoid CRTP. See [C++23’s Deducing this: what it is, why it is, how to use it](https://devblogs.microsoft.com/cppblog/cpp23-deducing-this/) – Remy Lebeau Jul 15 '23 at 22:42
  • OP can easy implement `class MatrixBase` or `class MatrixImpl` with type independent members and use it as a default template parameter in `Matrix`. – 273K Jul 15 '23 at 22:47