/* Matrix.cpp */

#include "Matrix.h"
#include <iostream>
#include <iomanip>

using namespace std;


// Global functions:
// A constructor should be used, but not introduced yet.
Matrix *createMatrix() {
  Matrix *m = new Matrix;
  m->nofRows = 0;
  m->nofCols = 0;
  m->elements = 0;
  return m;
}



// A destructor should be used, but not introduced yet.
void cleanupMatrix(Matrix *m) {
  m->depopulate();
  delete m;
}




// Member functions:
void Matrix::setSize(int nofRows, int nofCols) {
  if (nofRows * nofCols == 0) {
    return;
  }

  this->nofRows = nofRows;
  this->nofCols = nofCols;
  elements = new int[nofRows * nofCols];
}



void Matrix::resize(int nofRows, int nofCols) {
  if (nofRows * nofCols * this->nofRows * this->nofCols == 0) return;
  if (nofRows == this->nofRows && nofCols == this->nofCols) return;

  int *elems = new int[nofRows * nofCols];

  for (int i = 0; i < nofRows; ++i) {
    if (i < this->nofRows) {
      for (int j = 0; j < nofCols; ++j) {
        if (j < this->nofCols) {
          *(elems + i * nofCols + j) = *(elements + i * this->nofCols + j);
        }
        else {
          *(elems + i * nofCols + j) = 0;
        }
      }
    }
    else {
      for (int j = 0; j < nofCols; ++j) {
        *(elems + i * nofCols + j) = 0;
      }
    }
  }

  delete[] elements;
  this->nofRows = nofRows;
  this->nofCols = nofCols;
  elements = elems;
}



void Matrix::populate(int *ip) {
  for (int i = 0; i < nofRows * nofCols; ++i) {
    *(elements + i) = *(ip + i);
  }
}



void Matrix::print() {
  for (int i = 0; i < nofRows; ++i) {
    for (int j = 0; j < nofCols; ++j) {
      cout << setw(4) << *(elements + i * nofCols + j);
    }
    cout << endl;
  }
  cout << endl;
}



void Matrix::depopulate() {
  if (nofRows * nofCols == 0) {
    return;
  }

  this->nofRows = 0;
  this->nofCols = 0;
  delete[] elements;
}
