// Authors: Unknown. Please, if you are the author of this file, or if you // know who are the authors of this file, let us know, so we can give the // adequate credits and/or get the adequate authorizations. #ifndef MATRIX_H #define MATRIX_H #include #include namespace libNumerics { // Forward declaration, definition below template class vector; template class matrix; template matrix cat(const matrix&, const matrix&); template void swap(matrix&, matrix&); /// Matrix class template class matrix { public: static matrix zeros(int m) { return zeros(m,m); } static matrix zeros(int m, int n); static matrix ones(int m) { return ones(m,m); } static matrix ones(int m, int n); static matrix eye(int n); ///< Identity matrix. public: matrix(int m, int n); matrix(const matrix& m); virtual ~matrix(); matrix& operator=(const matrix& m); int nrow() const { return m_rows; } ///< The number of rows. int ncol() const { return m_cols; } ///< The number of columns. T operator() (int i, int j) const; T& operator() (int i, int j); T operator() (int i) const; T& operator() (int i); void operator=(T a); matrix operator*(T a) const; matrix operator/(T a) const; void operator*=(T a); void operator/=(T a); /// Product by scalar. friend matrix operator*(T a, const matrix& m) { return m * a; } matrix operator+(const matrix& m) const; matrix operator-(const matrix& m) const; matrix operator-() const; ///< Matrix opposite. matrix operator*(const matrix& m) const; vector operator*(const vector& m) const; void operator+=(const matrix& m); void operator-=(const matrix& m); matrix t() const; ///< Transpose. vector diag() const; ///< Diagonal of matrix. T tr() const; T det() const; matrix inv() const; void symUpper(); void symLower(); matrix copy(int i0, int i1, int j0, int j1) const; matrix copyCols(int j0, int j1) const; matrix copyRows(int i0, int i1) const; void paste(int i0, int j0, const matrix& block); friend matrix cat(const matrix& left, const matrix& right); vector col(int j) const; ///< Copy column. matrix row(int i) const; ///< Copy row. int lastCol() const {return m_cols-1;} ///< Index of last column. int lastRow() const {return m_rows-1;} ///< Index of last row. friend void swap(matrix&, matrix&); void swapRows(int i0, int i1); void swapCols(int j0, int j1); template void read(const U* v); void read(const matrix& v); void write(T* vect) const; protected: int m_rows; ///< Number of rows. int m_cols; ///< Number of columns. T* p; ///< 1-D array of coefficients. void alloc(int m, int n); ///< Allocate the array value. void free(); ///< Free the array value. int nElements() const; ///< Number of elements in the matrix. matrix& sub(matrix& s, int i, int j) const; }; // class matrix /// Column vector class (template) template class vector : public matrix { public: explicit vector(int m); vector(T x); vector(T x, T y); vector(T x, T y, T z); vector(const vector& v); virtual ~vector() {} using matrix::operator=; vector& operator=(const vector& v); // void operator=(T a); vector operator*(T a) const; vector operator/(T a) const; /// Product of a vector by a scalar. friend vector operator*(T a, const vector& v) { return v * a; } vector operator+(const vector& v) const; vector operator-(const vector& v) const; vector operator-() const; ///< Vector opposite. matrix operator*(const matrix& m) const; matrix diag() const; T qnorm() const; vector copy(int i0, int i1) const; void paste(int i0, const vector& v); }; } // namespace libNumerics /// Output matrix coefficients. template inline std::ostream& operator<<(std::ostream& out, const libNumerics::matrix& m) { for(int i = 0; i < m.nrow(); ++i) { out << ((i==0)? "[": ";"); for (int j = 0; j < m.ncol(); ++j) out << " " << m(i,j); } out << " ]"; return out; } /// Input matrix. Need to know the dimensions in advance... template inline std::istream& operator>>(std::istream& in, libNumerics::matrix& m) { char c; for(int i=0; i < m.nrow(); ++i) { in >> c; for(int j=0; j < m.ncol(); ++j) in >> m(i,j); } in >> c; return in; } template T dot(const libNumerics::vector& u, const libNumerics::vector& v); template libNumerics::vector cross(const libNumerics::vector& u, const libNumerics::vector& v); // Need to see definitions for templates... #include "matrix.cpp" #include "vector.cpp" #endif