
#ifndef VEC_MATRIX_H
#define VEC_MATRIX_H 

#include <iostream>

///General matrix-class for VecFloat-matrices of arbitrary size. 
class VecMatrix
{
  //member variables
private:
  int row;
  int column;

public:  
  VecFloat** m;

  //constructors / destructors  
public:
  ///Default constructor. 
  inline VecMatrix();

  ///Constructs a matrix instance with 'rowNr' rows and 'colNr' columns and initializes them with zero.
  inline VecMatrix(int rowNr, int colNr);

  ///Constructs a matrix instance from the matrix M.
  inline VecMatrix(const VecMatrix& M);

  ///Destructor of the matrix instance. 
  inline ~VecMatrix();

  //public member functions  
public:  

  ///Set all values of the matrix to zero. 
  inline void clear();

  ///Returns the determinant of the matrix. Just the standard algortihm and therefore not very fast.
  virtual inline VecFloat determinant();

  ///Get the number of columns of the matrix.
  inline int getcolumn() const;

  ///Get the number of rows of the matrix.
  inline int getrow() const;

  ///Inverts the matrix. Only implemented for size <=2. For size 3 use class DclMatrix33::public DclMatrix
  virtual inline bool inverse();

  //MB: I guess the following function is only fast if the matrix-instance already has the right size. 
  ///Multiplies a1*a2 into the matrix instance if a1.column = a2.row, else do nothing
  virtual inline void multiply(const VecMatrix& a1, const VecMatrix& a2);

  inline VecMatrix subMat(int,int,int,int); 

  ///Transpose the matrix. 
  inline void transpose();

  ///This operator substracts a matrix from the matrix instance and returns the result. The matrix instance is unchanged. 
  inline VecMatrix operator-(const VecMatrix&) const;

  //This operator adds a matrix to the matrix instance and returns the result. The matrix instance is unchanged. 
  virtual inline VecMatrix operator+(const VecMatrix&) const;

  ///This operator multiplies a matrix with the matrix instance and returns the result. The matrix instance is unchanged. 
  virtual inline VecMatrix operator*(const VecMatrix&) const;

  ///This operator equates the matrix instance with another matrix and returns a reference to the matrix-instance for concatenation.
  inline VecMatrix& operator=(const VecMatrix&);

  ///This operator multiplies all values of the matrix with a constant and return the result. The matrix instance is unchanged. 
  inline VecMatrix operator*(const VecFloat) const;

  inline VecMatrix& operator*=(const VecFloat); 

  //inline VECTOR operator*(const VECTOR&) const; //TODO implement vector multiplication with general vector

  ///This operator gives access to the entries of the matrix instance.
  inline VecFloat& operator()(int, int);

  ///This operator gives access to the entries of the matrix instance.
  inline const VecFloat& operator()(int, int) const;



  ///private member functions
private: 
  ///Returns the minor of the matrix instance with discarded row 'rowId' and discarded column 'colId'. 
  inline VecFloat minorMatrixdet(const int rowId, const int colId); 
public:	
  ///Multiplies the matrix instance from left with constant d and returns the result. The matrix instance is unchanged. 
  inline friend VecMatrix operator*(const VecFloat d, const VecMatrix&);

  inline friend std::ostream& operator<< (std::ostream&, const VecMatrix&); 
};


#include "matrix.inl"

#endif //VEC_MATRIX_H

