Ocean
Loading...
Searching...
No Matches
SparseMatrix.h
Go to the documentation of this file.
1/*
2 * Copyright (c) Meta Platforms, Inc. and affiliates.
3 *
4 * This source code is licensed under the MIT license found in the
5 * LICENSE file in the root directory of this source tree.
6 */
7
8#ifndef META_OCEAN_MATH_SPARSE_MATRIX_H
9#define META_OCEAN_MATH_SPARSE_MATRIX_H
10
11#include "ocean/math/Math.h"
12#include "ocean/math/Matrix.h"
13
14#include <vector>
15
16namespace Ocean
17{
18
19// Forward declaration.
20template <typename T> class MatrixT;
21
22// Forward declaration.
23template <typename T> class SparseMatrixT;
24
25/**
26 * Definition of the SparseMatrix object, depending on the OCEAN_MATH_USE_SINGLE_PRECISION either with single or double precision float data type.
27 * @see SparseMatrixT
28 * @ingroup math
29 */
31
32/**
33 * Instantiation of the SparseMatrixT template class using a double precision float data type.
34 * @see SparseMatrixT
35 * @ingroup math
36 */
38
39/**
40 * Instantiation of the SparseMatrixT template class using a single precision float data type.
41 * @see SparseMatrixT
42 * @ingroup math
43 */
45
46/**
47 * Definition of a vector holding sparse matrix objects.
48 * @see SparseMatrix
49 * @ingroup math
50 */
51typedef std::vector<SparseMatrix> SparseMatrices;
52
53/**
54 * This class implements a sparse matrix using a float type for its elements that is specified by T.
55 * @tparam T Data type of matrix elements
56 * @see SparseMatrix, SparseMatrixF, SparseMatrixD, Matrix.
57 * @ingroup math
58 */
59template <typename T>
61{
62 public:
63
64 // Forward declaration.
65 class Entry;
66
67 /**
68 * Definition of a vector holding entries.
69 */
70 typedef std::vector<Entry> Entries;
71
72 /**
73 * This class implements a triple object for matrix entries.
74 */
75 class OCEAN_MATH_EXPORT Entry
76 {
77 public:
78
79 /**
80 * Creates an invalid entry object.
81 */
82 inline Entry();
83
84 /**
85 * Creates a new entry object.
86 * @param row The row of the entry
87 * @param column The column of the entry
88 * @param value The value of the entry
89 */
90 inline Entry(const size_t row, const size_t column, const T value);
91
92 /**
93 * Returns the row of this entry
94 * @return The row
95 */
96 inline size_t row() const;
97
98 /**
99 * Returns the column of this entry
100 * @return The column
101 */
102 inline size_t column() const;
103
104 /**
105 * Returns the value of this entry
106 * @return The value
107 */
108 inline T value() const;
109
110 /**
111 * Returns whether this entry is valid.
112 * @return True, if so
113 */
114 inline bool isValid() const;
115
116 /**
117 * Compares two entries and returns whether this entry is 'lesser' than the second entry.
118 * Beware: The result is composed only on the coordinate of this entry, not on the value (thus, two entries with same coordinate but different value count as identical).
119 * @param second The second entry to compare
120 * @return True, if so
121 */
122 inline bool operator<(const Entry& second) const;
123
124 /**
125 * Checks whether a set of given entries have at least one entry in each row and in each column of a matrix with defined dimension.
126 * @param rows The number of rows of the matrix, with range [1, infinity)
127 * @param columns The number of columns of the matrix, with range [1, infinity)
128 * @param entries The entries to check
129 * @return True, if so
130 */
131 static bool hasOneEntry(const size_t rows, const size_t columns, const Entries& entries);
132
133 protected:
134
135 /// The row of this entry.
136 size_t entryRow;
137
138 /// The column of this entry.
140
141 /// The value of this entry.
143 };
144
145 public:
146
147 /**
148 * Creates an empty sparse matrix object.
149 */
151
152 /**
153 * Copy constructor.
154 * @param matrix Sparse matrix to be copied
155 */
157
158 /**
159 * Move constructor.
160 * @param matrix Sparse matrix to be movied
161 */
162 SparseMatrixT(SparseMatrixT<T>&& matrix) noexcept;
163
164 /**
165 * Creates a new spare matrix with given dimensions.
166 * @param rows Number of rows to create a sparse matrix for
167 * @param columns Number of columns to create a sparse matrix for
168 */
169 SparseMatrixT(const size_t rows, const size_t columns);
170
171 /**
172 * Creates a new spare matrix with given dimensions.
173 * @param rows Number of rows to create a sparse matrix for
174 * @param columns Number of columns to create a sparse matrix for
175 * @param nonZeroElements Number of expected non zero elements to reserve memory for
176 */
177 SparseMatrixT(const size_t rows, const size_t columns, const size_t nonZeroElements);
178
179 /**
180 * Creates a new spare matrix with given dimensions.
181 * @param rows Number of rows to create a sparse matrix for
182 * @param columns Number of columns to create a sparse matrix for
183 * @param entries All non-zero entries of the new matrix
184 */
185 SparseMatrixT(const size_t rows, const size_t columns, const Entries& entries);
186
187 /**
188 * Creates a new sparse matrix with defined rows and columns and initializes the diagonal with small sub matrices.
189 * The number of columns of the given diagonal vector matrix defines the size of the small sub matrices.<br>
190 * The number of rows of the diagonal vector matrix must be a multiple of the number of rows.<br>
191 * @param rows Rows of the new matrix
192 * @param columns Columns of the new matrix
193 * @param diagonal Diagonal vector matrix holding the new diagonal sub matrices
194 * @param forceNonZeros True, to force all diagonal elements to be an epsilon larger than zero (if the given element is zero)
195 */
196 SparseMatrixT(const size_t rows, const size_t columns, const MatrixT<T>& diagonal, const bool forceNonZeros = false);
197
198 /**
199 * Creates a new sparse matrix with defined rows and columns and copies all non-zero values from a dense matrix.
200 * @param denseMatrix Dense matrix from that the non-zero values are copied
201 */
203
204 /**
205 * Destructs a sparse matrix object.
206 */
208
209 /**
210 * Returns the number of rows this matrix has
211 * @return Number of rows
212 */
213 size_t rows() const;
214
215 /**
216 * Returns the number of columns this matrix has.
217 * @return Number of columns
218 */
219 size_t columns() const;
220
221 /**
222 * Returns the number of non zero elements stored in this matrix.
223 * @return Number of non zero elements
224 */
225 size_t nonZeroElements() const;
226
227 /**
228 * Returns a vector containing the values of the diagonal.
229 * @return Vector with diagonal values with dimension n x 1
230 */
232
233 /**
234 * Reserves memory for a specified number of non zero elements.
235 * @param elements Number of non zero elements.
236 */
237 void reserve(const size_t elements);
238
239 /**
240 * Returns whether a specified elements is zero.
241 * @param row The row of the element to be checked
242 * @param column The column of the element to be checked
243 * @return True, if so
244 */
245 bool isZero(const size_t row, const size_t column) const;
246
247 /**
248 * Returns whether two matrices are almost identical up to a specified epsilon.
249 * @param matrix Second matrix that will be checked
250 * @param eps Epsilon to be used
251 * @return True, if so
252 */
253 bool isEqual(const SparseMatrixT<T>& matrix, const T eps) const;
254
255 /**
256 * Returns whether two matrices are almost identical up to a specified epsilon.
257 * @param matrix Second matrix that will be checked
258 * @param eps Epsilon to be used
259 * @return True, if so
260 */
261 bool isEqual(const MatrixT<T>& matrix, const T eps) const;
262
263 /**
264 * (Re-)sets the non-zero entries of this sparse matrix.
265 * All previous non-zero entries will be removed.<br>
266 * If the given set of entries contains zero-values these zero values will be skipped.
267 * @param entries The entries to set
268 */
269 void setEntries(const Entries& entries);
270
271 /**
272 * Returns a submatrix of this matrix.
273 * @param row The index of the row which will be the first row of the new submatrix, with range [0, rows())
274 * @param column The index of the column which will be the first column of the new sub-matrix, with range [0, colums())
275 * @param rows The number of rows of the new sub-matrix, with range [1, rows() - row]
276 * @param columns The number of columns of the new sub-matrix, with range [1, columns() - column]
277 * @return The specified submatrix of this matrix
278 */
279 SparseMatrixT<T> submatrix(const size_t row, const size_t column, const size_t rows, const size_t columns) const;
280
281 /**
282 * Returns the transposes matrix of this matrix.
283 * @return Transposes matrix of this matrix
284 */
286
287 /**
288 * Transposes this matrix.
289 */
290 void transpose();
291
292 /**
293 * Solves the given linear system.
294 * M * x = b, with M and b known.<br>
295 * This matrix is M, the given vector is b and the result will be x.<br>
296 * @param b Vector defining the linear system
297 * @param x Solution vector receiving the solution if existing
298 * @return True, if succeeded
299 */
300 bool solve(const MatrixT<T>& b, MatrixT<T>& x) const;
301
302 /**
303 * Computes the rank of this matrix.
304 * The matrix must be valid.
305 * @return The matrix's rank with range [0, min(rows(), columns())]
306 */
307 size_t rank() const;
308
309 /**
310 * Determines the sum of all elements of this matrix.
311 * @return Matrix sum
312 */
313 inline T sum() const;
314
315 /**
316 * Inverts this square diagonal matrix.
317 * @return True, if succeeded
318 */
320
321 /**
322 * Inverts this square block diagonal matrix with 3x3 block size.
323 * The size of the matrix must be a multiple of three.<br>
324 * Each of the 3x3 block is inverted individually.<br>
325 * @return True, if succeeded
326 */
328
329 /**
330 * Inverts this square block diagonal matrix with size x size block size.
331 * The size of the matrix must be a multiple of size.<br>
332 * Each of the size x size block is inverted individually.<br>
333 * @param size The size of the block (size x size) with range (2, infinity)
334 * @return True, if succeeded
335 */
336 bool invertBlockDiagonal(const size_t size);
337
338 /**
339 * Returns the dense matrix of this matrix.
340 * @return Dense matrix
341 */
343
344 /**
345 * Performs a non-negative matrix factorization with multiplicative update rules
346 * V = W * H, V is a matrix containing non-negative values<br>
347 * This matrix is V, and will be factorized into two matrices W (weights) and H (subcomponents).
348 * @param subcomponents Solution matrix containing base component vectors
349 * @param weights Solution matrix containing weights to the component vectors
350 * @param components Number of base component vectors (Number of components is usally much smaller than its rank). If set to 0, the rank of matrix is used [0, rank]
351 * @param iterations Number of iterations maximal performed [1, infinity)
352 * @param convergenceThreshold Differential threshold as convergence criterion (0, infinity)
353 * @return True, if succeeded
354 */
355 bool nonNegativeMatrixFactorization(MatrixT<T>& subcomponents, MatrixT<T>& weights, const unsigned int components = 0u, const unsigned int iterations = 100u, const T convergenceThreshold = T(0.0001)) const;
356
357 /**
358 * Assign operator.
359 * @param matrix Sparse matrix to be assigned to this matrix
360 * @return Reference to this matrix
361 */
363
364 /**
365 * Move operator.
366 * @param matrix Sparse matrix to be move to this matrix
367 * @return Reference to this matrix
368 */
370
371 /**
372 * Multiplies two sparse matrix objects and returns the matrix result.
373 * @param matrix Right sparse matrix to multiply
374 * @return Matrix product result
375 */
377
378 /**
379 * Multiplies a second sparse matrix object to this matrix object.
380 * @param matrix Right sparse matrix to multiply
381 * @return Reference to this (modified) sparse matrix
382 */
383 inline SparseMatrixT<T>& operator*=(const SparseMatrixT<T>& matrix);
384
385 /**
386 * Adds two sparse matrix objects and returns the matrix result.
387 * @param matrix Right sparse matrix to add
388 * @return Matrix result
389 */
391
392 /**
393 * Adds a second sparse matrix object to this matrix.
394 * @param matrix Right sparse matrix to add
395 * @return Reference to this (modified) matrix
396 */
398
399 /**
400 * Subtracts two sparse matrix objects and returns the matrix result.
401 * @param matrix Right sparse matrix to subtract
402 * @return Matrix result
403 */
405
406 /**
407 * Subtracts a second sparse matrix object from this matrix.
408 * @param matrix Right sparse matrix to subtract
409 * @return Reference to this (modified) matrix
410 */
412
413 /**
414 * Multiplies a dense matrix object on this sparse matrix object and returns the dense matrix result.
415 * @param matrix Right matrix to multiply
416 * @return Matrix product result
417 */
418 MatrixT<T> operator*(const MatrixT<T>& matrix) const;
419
420 /**
421 * Returns whether this matrix is equal to an other one up to an epsilon value.
422 * @param matrix Second matrix to compare
423 * @return True, if succeeded
424 */
425 bool operator==(const SparseMatrixT<T>& matrix) const;
426
427 /**
428 * Returns whether this matrix is equal to an other one up to an epsilon value.
429 * @param matrix Second matrix to compare
430 * @return True, if succeeded
431 */
432 bool operator==(const MatrixT<T>& matrix) const;
433
434 /**
435 * Returns a specific element of the sparse matrix.
436 * @param row Element row to be returned
437 * @param column Element column to be returned
438 * @return Matrix element
439 */
440 T operator()(const size_t row, const size_t column) const;
441
442 /**
443 * Returns the reference to a specific element of the sparse matrix.
444 * Beware: The element must be non zero, thus the element must have been inserted before!
445 * @param row Element row to be returned
446 * @param column Element column to be returned
447 * @return Matrix element
448 * @see insert().
449 */
450 T& operator()(const size_t row, const size_t column);
451
452 private:
453
454 /**
455 * Creates a new sparse matrix object by the internal matrix object data directly.
456 * @param matrix Internal matrix object
457 */
458 explicit SparseMatrixT<T>(void* matrix);
459
460 private:
461
462 /// Abstract pointer to the internal matrix object.
464};
465
466template <typename T>
468 entryRow(size_t(-1)),
469 entryColumn(size_t(-1)),
470 entryValue(T(0))
471{
472 // nothing to do here
473}
474
475template <typename T>
476inline SparseMatrixT<T>::Entry::Entry(const size_t row, const size_t column, const T value) :
477 entryRow(row),
478 entryColumn(column),
479 entryValue(value)
480{
481 // nothing to do here
482}
483
484template <typename T>
485inline size_t SparseMatrixT<T>::Entry::row() const
486{
487 return entryRow;
488}
489
490template <typename T>
492{
493 return entryColumn;
494}
495
496template <typename T>
498{
499 return entryValue;
500}
501
502template <typename T>
504{
505 return entryRow != size_t(-1) && entryColumn != size_t(-1);
506}
507
508template <typename T>
509inline bool SparseMatrixT<T>::Entry::operator<(const Entry& second) const
510{
511 return entryRow < second.entryRow || (entryRow == second.entryRow && entryColumn < second.entryColumn);
512}
513
514template <typename T>
516{
517 *this = (*this) * matrix;
518 return *this;
519}
520
521template <typename T>
522inline bool SparseMatrixT<T>::operator==(const SparseMatrixT<T>& matrix) const
523{
524 return isEqual(matrix, NumericT<T>::eps());
525}
526
527template <typename T>
528inline bool SparseMatrixT<T>::operator==(const MatrixT<T>& matrix) const
529{
530 return isEqual(matrix, NumericT<T>::eps());
531}
532
533}
534
535#endif // META_OCEAN_MATH_SPARSE_MATRIX_H
This class implements a matrix with arbitrary size.
Definition Matrix.h:63
This class provides basic numeric functionalities.
Definition Numeric.h:57
This class implements a triple object for matrix entries.
Definition SparseMatrix.h:76
bool isValid() const
Returns whether this entry is valid.
Definition SparseMatrix.h:503
size_t column() const
Returns the column of this entry.
Definition SparseMatrix.h:491
T value() const
Returns the value of this entry.
Definition SparseMatrix.h:497
size_t entryRow
The row of this entry.
Definition SparseMatrix.h:136
size_t entryColumn
The column of this entry.
Definition SparseMatrix.h:139
static bool hasOneEntry(const size_t rows, const size_t columns, const Entries &entries)
Checks whether a set of given entries have at least one entry in each row and in each column of a mat...
bool operator<(const Entry &second) const
Compares two entries and returns whether this entry is 'lesser' than the second entry.
Definition SparseMatrix.h:509
Entry()
Creates an invalid entry object.
Definition SparseMatrix.h:467
size_t row() const
Returns the row of this entry.
Definition SparseMatrix.h:485
T entryValue
The value of this entry.
Definition SparseMatrix.h:142
This class implements a sparse matrix using a float type for its elements that is specified by T.
Definition SparseMatrix.h:61
void reserve(const size_t elements)
Reserves memory for a specified number of non zero elements.
bool invertBlockDiagonal3()
Inverts this square block diagonal matrix with 3x3 block size.
T sum() const
Determines the sum of all elements of this matrix.
SparseMatrixT(const size_t rows, const size_t columns, const Entries &entries)
Creates a new spare matrix with given dimensions.
bool isZero(const size_t row, const size_t column) const
Returns whether a specified elements is zero.
SparseMatrixT< T > & operator=(const SparseMatrixT< T > &matrix)
Assign operator.
bool isEqual(const SparseMatrixT< T > &matrix, const T eps) const
Returns whether two matrices are almost identical up to a specified epsilon.
SparseMatrixT< T > transposed() const
Returns the transposes matrix of this matrix.
SparseMatrixT(const size_t rows, const size_t columns)
Creates a new spare matrix with given dimensions.
SparseMatrixT< T > & operator+=(const SparseMatrixT< T > &matrix)
Adds a second sparse matrix object to this matrix.
size_t rows() const
Returns the number of rows this matrix has.
SparseMatrixT(const MatrixT< T > &denseMatrix)
Creates a new sparse matrix with defined rows and columns and copies all non-zero values from a dense...
bool isEqual(const MatrixT< T > &matrix, const T eps) const
Returns whether two matrices are almost identical up to a specified epsilon.
size_t nonZeroElements() const
Returns the number of non zero elements stored in this matrix.
SparseMatrixT< T > operator-(const SparseMatrixT< T > &matrix) const
Subtracts two sparse matrix objects and returns the matrix result.
~SparseMatrixT()
Destructs a sparse matrix object.
MatrixT< T > denseMatrix() const
Returns the dense matrix of this matrix.
SparseMatrixT< T > & operator-=(const SparseMatrixT< T > &matrix)
Subtracts a second sparse matrix object from this matrix.
SparseMatrixT(const SparseMatrixT< T > &matrix)
Copy constructor.
SparseMatrixT< T > operator+(const SparseMatrixT< T > &matrix) const
Adds two sparse matrix objects and returns the matrix result.
std::vector< Entry > Entries
Definition of a vector holding entries.
Definition SparseMatrix.h:70
void * internalMatrix
Abstract pointer to the internal matrix object.
Definition SparseMatrix.h:463
SparseMatrixT()
Creates an empty sparse matrix object.
size_t columns() const
Returns the number of columns this matrix has.
void setEntries(const Entries &entries)
(Re-)sets the non-zero entries of this sparse matrix.
bool solve(const MatrixT< T > &b, MatrixT< T > &x) const
Solves the given linear system.
bool operator==(const SparseMatrixT< T > &matrix) const
Returns whether this matrix is equal to an other one up to an epsilon value.
Definition SparseMatrix.h:522
void transpose()
Transposes this matrix.
bool invertDiagonal()
Inverts this square diagonal matrix.
bool invertBlockDiagonal(const size_t size)
Inverts this square block diagonal matrix with size x size block size.
size_t rank() const
Computes the rank of this matrix.
SparseMatrixT(const size_t rows, const size_t columns, const size_t nonZeroElements)
Creates a new spare matrix with given dimensions.
SparseMatrixT< T > & operator*=(const SparseMatrixT< T > &matrix)
Multiplies a second sparse matrix object to this matrix object.
Definition SparseMatrix.h:515
bool nonNegativeMatrixFactorization(MatrixT< T > &subcomponents, MatrixT< T > &weights, const unsigned int components=0u, const unsigned int iterations=100u, const T convergenceThreshold=T(0.0001)) const
Performs a non-negative matrix factorization with multiplicative update rules V = W * H,...
MatrixT< T > diagonal() const
Returns a vector containing the values of the diagonal.
SparseMatrixT(const size_t rows, const size_t columns, const MatrixT< T > &diagonal, const bool forceNonZeros=false)
Creates a new sparse matrix with defined rows and columns and initializes the diagonal with small sub...
MatrixT< T > operator*(const MatrixT< T > &matrix) const
Multiplies a dense matrix object on this sparse matrix object and returns the dense matrix result.
SparseMatrixT< T > operator*(const SparseMatrixT< T > &matrix) const
Multiplies two sparse matrix objects and returns the matrix result.
SparseMatrixT(SparseMatrixT< T > &&matrix) noexcept
Move constructor.
SparseMatrixT< T > & operator=(SparseMatrixT< T > &&matrix) noexcept
Move operator.
SparseMatrixT< T > submatrix(const size_t row, const size_t column, const size_t rows, const size_t columns) const
Returns a submatrix of this matrix.
T & operator()(const size_t row, const size_t column)
Returns the reference to a specific element of the sparse matrix.
T operator()(const size_t row, const size_t column) const
Returns a specific element of the sparse matrix.
std::vector< SparseMatrix > SparseMatrices
Definition of a vector holding sparse matrix objects.
Definition SparseMatrix.h:51
SparseMatrixT< Scalar > SparseMatrix
Definition of the SparseMatrix object, depending on the OCEAN_MATH_USE_SINGLE_PRECISION either with s...
Definition SparseMatrix.h:30
SparseMatrixT< double > SparseMatrixD
Instantiation of the SparseMatrixT template class using a double precision float data type.
Definition SparseMatrix.h:37
SparseMatrixT< float > SparseMatrixF
Instantiation of the SparseMatrixT template class using a single precision float data type.
Definition SparseMatrix.h:44
The namespace covering the entire Ocean framework.
Definition Accessor.h:15