      1  using namespace std;
      2
      3  #include <iomanip>
      4  #include <sstream>
      5  #include "matrix4.h"
      6
      7  namespace BigCPlusPlus_Matrix
      8  {
      9
     10  string Matrix::IndexException::format_message(int n)
     11  {
     12     ostringstream outstr;
     13     outstr << "Matrix index " << n << " out of range";
     14     return outstr.str();
     15  }
     16
     17  Matrix::Matrix(int r, int c)
     18  {
     19     rows = r;
     20     columns = c;
     21     elements = new double[rows * columns];
     22     for (int i = 0; i < rows * columns; i++)
     23        elements[i] = 0;
     24  }
     25
     26  Matrix& Matrix::operator=(const Matrix& other)
     27  {
     28     if (this != &other)
     29     {
     30        free();
     31        copy(other);
     32     }
     33     return *this;
     34  }
     35
     36  void Matrix::copy(const Matrix& other)
     37  {
     38     rows = other.rows;
     39     columns = other.columns;
     40     elements = new double[rows * columns];
     41     for (int i = 0; i < rows * columns; i++)
     42        elements[i] = other.elements[i];
     43  }
     44
     45  double& Matrix::operator()(int i, int j)
     46  {
     47     if (i < 0 || i >= rows)
     48        throw Matrix::IndexException(i);
     49     if (j < 0 || j >= columns)
     50        throw Matrix::IndexException(j);
     51     return elements[i * get_columns() + j];
     52  }
     53
     54  double Matrix::operator()(int i, int j) const
     55  {
     56     if (i < 0 || i >= rows)
     57        throw Matrix::IndexException(i);
     58     if (j < 0 || j >= columns)
     59        throw Matrix::IndexException(j);
     60     return elements[i * get_columns() + j];
     61  }
     62
     63  Matrix& Matrix::operator+=(const Matrix& right)
     64  {
     65     if (rows != right.rows || columns != right.columns)
     66        throw Matrix::MismatchException();
     67     for (int i = 0; i < rows; i++)
     68        for (int j = 0; j < columns; j++)
     69           (*this)(i, j) += right(i, j);
     70     return *this;
     71  }
     72
     73  Matrix operator+(const Matrix& left, const Matrix& right)
     74  {
     75     Matrix result = left;
     76     result += right;
     77     return result;
     78  }
     79
     80  Matrix operator*(const Matrix& left, const Matrix& right)
     81  {
     82     if (left.get_columns() != right.get_rows())
     83        throw Matrix::MismatchException();
     84     Matrix result(left.get_rows(), right.get_columns());
     85     for (int i = 0; i < left.get_rows(); i++)
     86        for (int j = 0; j < right.get_columns(); j++)
     87           for (int k = 0; k < left.get_columns(); k++)
     88              result(i, j) += left(i, k) * right(k, j);
     89     return result;
     90  }
     91
     92  Matrix operator*(const Matrix& left, double right)
     93  {
     94     Matrix result(left);
     95     for (int i = 0; i < result.get_rows(); i++)
     96        for (int j = 0; j < result.get_columns(); j++)
     97           result(i, j) *= right;
     98     return result;
     99  }
    100
    101  ostream& operator<<(ostream& left, const Matrix& right)
    102  {
    103     const int WIDTH = 10;
    104     for (int i = 0; i < right.get_rows(); i++)
    105     {
    106        for (int j = 0; j < right.get_columns(); j++)
    107           left << setw(WIDTH) << right(i, j);
    108        left << "\n";
    109     }
    110     return left;
    111  }
    112
    113  }  // namespace BigCPlusPlus_Matrix