0

I am learning C++ and I have a Class declaration in a .h file, and the definitions on a .cpp file. The .h file is as follows:

// matrix.h

class Matrix {
 private:
  int r; // number of rows
  int c; // number of columns
  double* d;
 public:
  Matrix(int nrows, int ncols, double ini = 0.0); // declaration of the constructor
  ~Matrix(); // declaration of the destructor
  inline double operator()(int i, int j) const;
  inline double& operator()(int i, int j);
};

And the .cpp is:

// matrix.cpp

#include "matrix.h"

Matrix::Matrix(int nrows, int ncols, double ini) {
  r = nrows;
  c = ncols;
  d = new double[nrows*ncols];
  for (int i = 0; i < nrows*ncols; i++) d[i] = ini;
}

Matrix::~Matrix() {
  delete[] d;
}

inline double Matrix::operator()(int i, int j) const {
  return d[i*c+j];
}

inline double& Matrix::operator()(int i, int j) {
  return d[i*c+j];
}

And the test file is:

// test.cpp
#include <iostream>
#include "matrix.h"

using namespace std;

int main(int argc, char *argv[]) {
  Matrix neo(2,2,1.0);
  cout << (neo(0,0) = 2.34) << endl;
  return EXIT_SUCCESS;
}

Problem: when I compile the test.cpp file using g++ test.cpp, or using g++ test.cpp matrix.cpp, I get the errors: warning: inline function 'Matrix::operator()' is not defined and ld: symbol(s) not found for architecture x86_64.

Question: What is failing? How can I understand what is happening? Thanks for helping!

Guilherme Salomé
  • 1,899
  • 4
  • 19
  • 39
  • 2
    Get rid of the "inline" keyword everywhere you put it. Whatever you think it means, it doesn't mean that. – Sam Varshavchik Dec 21 '17 at 03:23
  • Either that or move the function implementations into the header, like `inline double& operator()(int i, int j) {return d[i*c+j];}` – zzxyz Dec 21 '17 at 03:25
  • @SamVarshavchik I am following a book, that's why I have it there. The book explains that: "(...) the body of the operator definition is inserted into the code as it is being compiled. This makes the resulting program larger, but saves the execution time required for a function call." Do you think that's causing the problem? How can I understand what's going on better? Thanks for helping! – Guilherme Salomé Dec 21 '17 at 03:26
  • 1
    @GuilhermeSalomé The book is correct, but for that work, the caller has to be able to directly see the function implementation. So in your case, it needs to be in the header. – zzxyz Dec 21 '17 at 03:27
  • 2
    Unrelated: A future bug will likely involve the Rule of Three. Forewarned is forearmed, so give this a read: https://stackoverflow.com/questions/4172722/what-is-the-rule-of-three . – user4581301 Dec 21 '17 at 03:28

1 Answers1

4

The body of an inline function should be visible at all callsites of the function.

In your setup you need to move those two inline definitions from matrix.cpp to matrix.h ; or make them non-inline.

M.M
  • 138,810
  • 21
  • 208
  • 365