22 #ifndef CRNMATRIX_HEADER
23 #define CRNMATRIX_HEADER
52 Matrix(
size_t nrow,
size_t ncol,
const T &value = T(0)) :
rows(nrow),
cols(ncol)
55 throw ExceptionDomain(
"Matrix::Matrix(size_t nrow, size_t ncol, double value): null or negative row or column dimensions");
64 Matrix(
const std::vector<std::vector<T>> &m)
68 if (m.front().empty())
71 auto c = m.front().size();
72 for (
const auto &line : m)
78 for (
size_t r = 0; r <
rows; ++r)
79 std::copy(m[r].begin(), m[r].end(),
data.begin() + r *
cols);
122 data = std::move(vect);
128 data = std::move(vect);
135 virtual ~Matrix()
override =
default;
140 std::copy(m.
Std().begin(), m.
Std().end(),
data.begin());
165 inline const T&
At(
size_t pos)
const noexcept {
return data[pos]; }
166 inline T&
At(
size_t pos) noexcept {
return data[pos]; }
167 inline const T&
At(
size_t r,
size_t c)
const noexcept {
return data[r *
cols + c]; }
168 inline T&
At(
size_t r,
size_t c) noexcept {
return data[r *
cols + c]; }
175 for (
size_t r = 0; r <
rows; ++r)
176 for (
size_t c = 0; c <
cols; ++c)
184 for (
size_t r = 0; r <
rows; ++r)
185 for (
size_t c = 0; c <
cols; ++c)
186 At(r, c) = -
At(r, c);
196 inline void SetRow(
size_t r,
const std::vector<T> &row)
200 if (row.size() !=
cols)
202 for (
size_t c = 0; c <
cols; ++c)
213 inline void SetColum(
size_t c,
const std::vector<T> &col)
217 if (col.size() !=
rows)
219 for (
size_t r = 0; r <
rows; ++r)
233 throw ExceptionDomain(
"Matrix::IncreaseElement(): index out of range.");
245 throw ExceptionDomain(
"Matrix::IncreaseRow(): column index out of range");
246 for (
size_t c = 0; c <
cols; ++c)
258 throw ExceptionDomain(
"Matrix::IncreaseColumn(): column index out of range");
259 for (
size_t r = 0; r <
rows; ++r)
284 for (
size_t r = 0; r <
rows; r++)
285 for (
size_t c = 0; c < m.
GetCols(); c++)
286 for (
size_t k = 0; k <
cols; k++)
287 p[r * m.
GetCols() + c] +=
At(r, k) * m[k][c];
296 return std::equal(
data.begin(),
data.end(), m.
data.begin());
299 {
return !(*
this == m); }
324 for (
size_t c = 0; c <
cols; ++c)
325 At(r, c) = T(v *
At(r, c));
336 throw ExceptionDomain(
"Matrix::ScaleColumn(): column index out of range");
337 for (
size_t r = 0; r <
rows; ++r)
338 At(r, c) = T(v *
At(r, c));
344 auto means = std::vector<T>(
cols, T(0));
345 for (
size_t r = 0; r <
rows; ++r)
346 for (
size_t c = 0; c <
cols; ++c)
347 means[c] +=
At(r, c);
348 for (
size_t c = 0; c <
cols; ++c)
349 means[c] = means[c] / T(rows);
350 for (
size_t r = 0; r <
rows; ++r)
351 for (
size_t c = 0; c <
cols; ++c)
352 At(r, c) -= means[c];
360 auto means = std::vector<T>(
cols, T(0));
363 for (
size_t r = 0; r <
rows; ++r)
364 for (
size_t c = 0; c <
cols; ++c)
365 means[c] +=
At(r, c);
366 for (
size_t c = 0; c <
cols; ++c)
367 means[c] = means[c] / T(rows);
369 auto devs = std::vector<T>(
cols, T(0));
370 for (
size_t r = 0; r <
rows; ++r)
371 for (
size_t c = 0; c <
cols; ++c)
372 devs[c] +=
Sqr(
At(r, c) - means[c]);
373 for (
size_t c = 0; c <
cols; ++c)
374 devs[c] = sqrt(devs[c] / T(rows));
375 for (
size_t r = 0; r <
rows; ++r)
376 for (
size_t c = 0; c <
cols; ++c)
390 for (
size_t c = 0; c <
cols; ++c)
391 std::swap(
At(r1, c),
At(r2, c));
404 for (
size_t r = 0; r <
rows; ++r)
405 std::swap(
At(r, c1),
At(r, c2));
412 for (
size_t r = 0; r <
rows; ++r)
413 for (
size_t c = 0; c <
cols; ++c)
414 sum +=
Abs(
At(r, c));
416 for (
size_t r = 0; r <
rows; ++r)
417 for (
size_t c = 0; c <
cols; ++c)
425 for (
size_t r = 0; r <
rows; r++)
426 for (
size_t c = 0; c <
cols; c++)
434 return *std::min_element(
data.begin(),
data.end());
440 return *std::max_element(
data.begin(),
data.end());
446 auto pos = std::min_element(
data.begin(),
data.end()) -
data.begin();
447 return std::make_pair(pos /
cols, pos %
cols);
453 auto pos = std::max_element(
data.begin(),
data.end()) -
data.begin();
454 return std::make_pair(pos /
cols, pos %
cols);
463 for (
size_t r = 0; r <
rows; ++r)
464 for (
size_t c = 0; c <
cols; ++c)
465 out[c][r] =
At(r, c);
475 for (
size_t r = 0; r <
rows; ++r)
476 for (
size_t c = 0; c <
cols; ++c)
477 newdata[c * rows + r] =
At(r, c);
479 std::swap(rows, cols);
492 throw ExceptionDomain(
"Matrix::MakeRowAsColumn(): index out of range");
516 throw ExceptionDomain(
"Matrix::MakeColumn(): column index out of range");
518 for (
size_t r = 0; r <
rows; r++)
519 column.At(r, 0) =
At(r, k);
531 return std::max_element(
data.begin() + r *
cols,
data.begin() + (r + 1) * cols) - (
data.begin() + r *
cols);
543 auto index = size_t(0);
544 for (
size_t r = 0; r <
rows; r++)
546 const auto &mrc =
At(r, c);
564 throw ExceptionDomain(
"Matrix::CountNullCellsInRow(): row index out of range");
565 return std::count(
data.begin() + r *
cols,
data.begin() + (r + 1) * cols, T(0));
576 throw ExceptionDomain(
"Matrix::CountNullCellsInColumn(): column index out of range");
577 auto count = size_t(0);
578 for (
size_t r = 0; r <
rows; ++r)
579 if (
At(r, c) == T(0))
587 return std::count(
data.begin(),
data.end(), T(0));
594 for (
size_t r = 0; r <
rows; ++r)
595 for (
size_t c = 0; c <
cols; ++c)
597 m *= 1.0 / double(rows);
605 for (
size_t r = 0; r <
rows; ++r)
606 for (
size_t c = 0; c <
cols; ++c)
607 m.At(c) +=
Sqr(
At(r, c) - means[c]);
608 m *= 1.0 / double(rows);
627 for (
size_t i = 0; i <
cols; ++i)
628 for (
size_t j = i; j <
cols; ++j)
631 for (
size_t k = 0; k <
rows; ++k)
632 product +=
At(k, i) *
At(k, j);
658 inline const std::vector<T>&
Std() const & noexcept {
return data; }
660 inline std::vector<T>
Std() && {
return std::move(
data); }
666 std::copy(
data.begin(),
data.end(), img.Begin());
676 for (
size_t r = 0; r <
rows; r++)
678 for (
size_t c = 0; c <
cols; c++)
700 {
return std::move(m1 += m2); }
702 {
return std::move(m2 += m1); }
707 {
return std::move(m1 -= m2); }
712 {
return std::move(m *= d); }
716 {
return std::move(m *= d); }
721 {
return std::move(m /= d); }
725 {
return std::move(m /= d); }
731 {
return std::move(m1 *= m2); }
BoolNotBoolDummy operator-(const BoolNotBoolDummy &, const BoolNotBoolDummy &)
String ToString() const
Prints matrix into a string.
ScalarRange< T > Range(T b, T e)
Creates a range [[b, e[[.
size_t GetRows() const noexcept
Returns the number of rows.
void SwapColumns(size_t c1, size_t c2)
Swap two columns in matrix.
void Negative()
Change sign for all elements.
size_t GetCols() const noexcept
Returns the number of columns.
T & At(size_t pos) noexcept
void IncreaseRow(size_t r, const T &v)
Increase one row from matrix.
Matrix(std::vector< T > &&vect, Orientation ori=Orientation::VERTICAL)
Constructor from std::vector 1D vector.
Orientation
An enumeration of orientations.
Matrix MakeCovariance() const
Matrix(const std::vector< T > &vect, Orientation ori=Orientation::VERTICAL)
Constructor from std::vector 1D vector.
Matrix & operator/=(double d)
Scaling.
const T * operator[](size_t r) const
Returns a row.
T * operator[](size_t r)
Returns a row.
virtual Matrix & Transpose()
Inplace transposition.
size_t CountNullCells() const
Matrix MakeRow(size_t r) const
Extract a row from current matrix.
Matrix MakeColumn(size_t k) const
Extracts one column from matrix.
bool operator!=(const Matrix &m) const
size_t CountNullCellsInColumn(size_t c) const
Counts null cells in column.
Matrix & operator*=(const Matrix &m)
size_t CountNullCellsInRow(size_t r) const
Counts null cells in row.
Matrix & operator*=(double d)
Scaling.
void ReduceColumns(bool centered=true)
Reduces all columns by dividing by the standard deviation of each column.
T & At(size_t r, size_t c) noexcept
A UTF32 character string class.
IMG ToImage() const
Converts to image.
const T & At(size_t r, size_t c) const noexcept
bool areValidIndexes(size_t r, size_t c) const
checks the validity of indexes
void NormalizeForConvolution()
Normalizes the matrix to be used for convolution.
Matrix MakeTranspose()
Create transposition.
BoolNotBoolDummy operator*(const BoolNotBoolDummy &, const BoolNotBoolDummy &)
void MultRow(size_t r, double v)
Scale one row from matrix.
decltype(std::declval< T >()+std::declval< T >()) SumType
A safe type to compute a sum (e.g.: a larger integer type)
BoolNotBoolDummy operator+(const BoolNotBoolDummy &, const BoolNotBoolDummy &)
constexpr SumType< T > Sqr(const T &v) noexcept(noexcept(v *v))
Returns the square of a value.
void SetAll(const T &v)
Set all elements.
void CenterColumns()
Centers all columns by subtracting the mean for each column.
void IncreaseColumn(size_t c, const T &v)
Increase one column from matrix.
std::vector< T > datatype
Matrix MakeColumnMeans() const
Matrix & operator+=(const Matrix &m)
void Abs(Image< T > &img, typename std::enable_if< std::is_arithmetic< T >::value >::type *dummy=nullptr) noexcept
Replaces each pixel by its absolute value.
Matrix & operator=(const Matrix &)=default
const T & At(size_t pos) const noexcept
Matrix MakeRowAsColumn(size_t r) const
Creates a column matrix from a row.
std::pair< size_t, size_t > Argmin() const
const std::vector< T > & Std() const &noexcept
void MultColumn(size_t c, double v)
Scale one column from matrix.
BoolNotBoolDummy operator/(const BoolNotBoolDummy &, const BoolNotBoolDummy &)
bool operator==(const Matrix &m) const
size_t ArgmaxInColumn(size_t c) const
Returns the row index of the maximal element in a column.
void SetColum(size_t c, const std::vector< T > &col)
Sets the values of a column.
virtual ~Matrix() override=default
Destructor.
size_t ArgmaxInRow(size_t r) const
Returns the row index of the maximal element in a row.
std::pair< size_t, size_t > Argmax() const
TypeInfo< T >::SumType CumulateCells() const
void SetRow(size_t r, const std::vector< T > &row)
Sets the values of a row.
Matrix MakeColumnDeviations(const Matrix &means) const
A class containing informations on a type.
Matrix MakeColumnDeviations(bool zero_means=false) const
standard deviation of patterns stored as the rows of a data matrix
void IncreaseElement(size_t r, size_t c, const T &delta)
Increases the value of an element.
Matrix(const Matrix< Y > &m)
Invalid argument error (e.g.: nullptr pointer)
Matrix & operator-=(const Matrix &m)
Matrix(size_t nrow, size_t ncol, const T &value=T(0))
Constructor.
Matrix(const std::vector< std::vector< T >> &m)
Constructor from std::vector matrix.
void SwapRows(size_t r1, size_t r2)
Swap two rows in matrix.