Line data Source code
1 : #pragma once
2 :
3 : #include "Arduino/ArduinoConfig.hpp"
4 :
5 : #include <algorithm> // std::fill, std::transform
6 : #include <cassert> // assert
7 : #include <cmath> // std::sqrt
8 : #include <functional> // std::plus, std::minus
9 : #include <numeric> // std::inner_product
10 : #include <utility> // std::swap
11 : #include <vector> // std::vector
12 :
13 : #ifndef NO_IOSTREAM_SUPPORT
14 : #include <iosfwd> // std::ostream
15 : #endif
16 :
17 : #ifndef NO_RANDOM_SUPPORT
18 : #include <random> // std::uniform_real_distribution
19 : #endif
20 :
21 : using std::size_t;
22 :
23 : #include "util/MatrixStorage.hpp"
24 :
25 : #ifndef COL_MAJ_ORDER
26 : #define COL_MAJ_ORDER 1
27 : #endif
28 :
29 : /// @addtogroup MatVec
30 : /// @{
31 :
32 : #ifndef NO_ARDUINO_PRINT_SUPPORT
33 : /// General matrix class.
34 : class Matrix : public Printable {
35 : #else
36 35 : class Matrix {
37 : #endif
38 :
39 : /// Container to store the elements of the matrix internally.
40 : using storage_t = util::storage_t<double>;
41 :
42 : protected:
43 : /// Convert raw storage to a matrix.
44 : explicit Matrix(storage_t &&storage, size_t rows, size_t cols);
45 : /// Convert raw storage to a matrix.
46 : explicit Matrix(const storage_t &storage, size_t rows, size_t cols);
47 :
48 : public:
49 : /// @name Constructors and assignment
50 : /// @{
51 :
52 : /// Default constructor.
53 393 : Matrix() = default;
54 :
55 : /// Create a matrix of zeros with the given dimensions.
56 : Matrix(size_t rows, size_t cols);
57 :
58 : /// Create a matrix with the given values.
59 : Matrix(std::initializer_list<std::initializer_list<double>> init);
60 : /// Assign the given values to the matrix.
61 : Matrix &
62 : operator=(std::initializer_list<std::initializer_list<double>> init);
63 :
64 : /// Default copy constructor.
65 27 : Matrix(const Matrix &) = default;
66 : /// Move constructor.
67 : Matrix(Matrix &&);
68 :
69 : /// Default copy assignment.
70 : Matrix &operator=(const Matrix &) = default;
71 : /// Move assignment.
72 : Matrix &operator=(Matrix &&);
73 :
74 : /// @}
75 :
76 : public:
77 : /// @name Matrix size
78 : /// @{
79 :
80 : /// Get the number of rows of the matrix.
81 5534 : size_t rows() const { return rows_; }
82 : /// Get the number of columns of the matrix.
83 4596 : size_t cols() const { return cols_; }
84 : /// Get the number of elements in the matrix:
85 197 : size_t num_elems() const { return storage.size(); }
86 :
87 : /// Reshape the matrix. The new size must have the same number of elements,
88 : /// and the result depends on the storage order (column major order or
89 : /// row major order).
90 : void reshape(size_t newrows, size_t newcols);
91 : /// Create a reshaped copy of the matrix.
92 : /// @see @ref reshape
93 : Matrix reshaped(size_t newrows, size_t newcols) const;
94 :
95 : /// @}
96 :
97 : public:
98 : /// @name Element access
99 : /// @{
100 :
101 : /// Get the element at the given position in the matrix.
102 : double &operator()(size_t row, size_t col);
103 : /// Get the element at the given position in the matrix.
104 : const double &operator()(size_t row, size_t col) const;
105 :
106 : /// Get the element at the given position in the linearized matrix.
107 298 : double &operator()(size_t index) { return storage[index]; }
108 : /// Get the element at the given position in the linearized matrix.
109 188 : const double &operator()(size_t index) const { return storage[index]; }
110 :
111 : /// @}
112 :
113 : public:
114 : /// @name Memory management
115 : /// @{
116 :
117 : /// Set the number of rows and columns to zero, and deallocate the storage.
118 : void clear_and_deallocate();
119 :
120 : /// @}
121 :
122 : public:
123 : /// @name Filling matrices
124 : /// @{
125 :
126 : /// Fill the matrix with a constant value.
127 : void fill(double value);
128 :
129 : /// Fill the matrix as an identity matrix (all zeros except the diagonal
130 : /// which is one).
131 : void fill_identity();
132 :
133 : #ifndef NO_RANDOM_SUPPORT
134 : /// Fill the matrix with uniformly distributed random values.
135 : void fill_random(double min = 0, double max = 1,
136 : std::default_random_engine::result_type seed =
137 : std::default_random_engine::default_seed);
138 : #endif
139 :
140 : /// @}
141 :
142 : public:
143 : /// @name Create special matrices
144 : /// @{
145 :
146 : /// Create a matrix filled with ones.
147 : static Matrix ones(size_t rows, size_t cols);
148 :
149 : /// Create a matrix filled with zeros.
150 : static Matrix zeros(size_t rows, size_t cols);
151 :
152 : /// Create a matrix filled with a constant value.
153 : static Matrix constant(size_t rows, size_t cols, double value);
154 :
155 : /// Create an identity matrix.
156 : static Matrix identity(size_t rows, size_t cols);
157 :
158 : /// Create a square identity matrix.
159 : static Matrix identity(size_t rows);
160 :
161 : #ifndef NO_RANDOM_SUPPORT
162 : /// Create a matrix with uniformly distributed random values.
163 : static Matrix random(size_t rows, size_t cols, double min = 0,
164 : double max = 1,
165 : std::default_random_engine::result_type seed =
166 : std::default_random_engine::default_seed);
167 : #endif
168 :
169 : /// @}
170 :
171 : public:
172 : /// @name Swapping rows and columns
173 : /// @{
174 :
175 : /// Swap two rows of the matrix.
176 : void swap_rows(size_t a, size_t b);
177 : /// Swap two columns of the matrix.
178 : void swap_columns(size_t a, size_t b);
179 :
180 : /// @}
181 :
182 : public:
183 : /// @name Comparison
184 : /// @{
185 :
186 : /// Check for equality of two matrices.
187 : /// @warning Uses exact comparison, which is often not appropriate for
188 : /// floating point numbers.
189 : bool operator==(const Matrix &other) const;
190 : /// Check for inequality of two matrices.
191 : /// @warning Uses exact comparison, which is often not appropriate for
192 : /// floating point numbers.
193 : bool operator!=(const Matrix &other) const { return !(*this == other); }
194 :
195 : /// @}
196 :
197 : public:
198 : /// @name Matrix norms
199 : /// @{
200 :
201 : /// Compute the Frobenius norm of the matrix.
202 : double normFro() const &;
203 : /// Compute the Frobenius norm of the matrix.
204 : double normFro() &&;
205 :
206 : /// @}
207 :
208 : public:
209 : /// @name Iterators
210 : /// @{
211 :
212 : /// Get the iterator to the first element of the matrix.
213 132 : storage_t::iterator begin() { return storage.begin(); }
214 : /// Get the iterator to the first element of the matrix.
215 428 : storage_t::const_iterator begin() const { return storage.begin(); }
216 : /// Get the iterator to the first element of the matrix.
217 : storage_t::const_iterator cbegin() const { return storage.begin(); }
218 :
219 : /// Get the iterator to the element past the end of the matrix.
220 52 : storage_t::iterator end() { return storage.end(); }
221 : /// Get the iterator to the element past the end of the matrix.
222 360 : storage_t::const_iterator end() const { return storage.end(); }
223 : /// Get the iterator to the element past the end of the matrix.
224 : storage_t::const_iterator cend() const { return storage.end(); }
225 :
226 : /// @}
227 :
228 : public:
229 : /// @name Printing
230 : /// @{
231 :
232 : #ifndef NO_IOSTREAM_SUPPORT
233 : /// Print a matrix.
234 : /// @param os
235 : /// The stream to print to.
236 : /// @param precision
237 : /// The number of significant figures to print.
238 : /// (0 = auto)
239 : /// @param width
240 : /// The width of each element (number of characters).
241 : /// (0 = auto)
242 : void print(std::ostream &os, uint8_t precision = 0,
243 : uint8_t width = 0) const;
244 : #endif
245 :
246 : #ifndef NO_ARDUINO_PRINT_SUPPORT
247 : /// Print a matrix
248 : /// @param print
249 : /// The printer to print to.
250 : /// @param precision
251 : /// The number of significant figures to print.
252 : /// (0 = auto)
253 : /// @param width
254 : /// The width of each element (number of characters).
255 : /// (0 = auto)
256 : void print(Print &print, uint8_t precision = 0, uint8_t width = 0) const;
257 :
258 : /// Implements the Arduino Printable interface.
259 : size_t printTo(Print &print) const override {
260 : this->print(print);
261 : return 0;
262 : }
263 : #endif
264 :
265 : /// @}
266 :
267 : protected:
268 : size_t rows_ = 0, cols_ = 0;
269 : storage_t storage;
270 :
271 : friend class Vector;
272 : friend class RowVector;
273 : };
274 :
275 : // :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: //
276 :
277 : /// A column vector (n×1 matrix).
278 : class Vector : public Matrix {
279 : public:
280 : /// @name Constructors and assignment
281 : /// @{
282 :
283 : /// Default constructor.
284 12 : Vector() = default;
285 :
286 : /// Create a column vector of the given size.
287 : Vector(size_t size) : Matrix(size, 1) {}
288 :
289 : /// Create a column vector from the given list of values.
290 136 : Vector(std::initializer_list<double> init) { *this = init; }
291 :
292 : /// Assign a list of values to the column vector.
293 : Vector &operator=(std::initializer_list<double> init);
294 :
295 : /// Convert an m×n matrix to a mn column vector.
296 : explicit Vector(const Matrix &matrix);
297 : /// Convert an m×n matrix to a mn column vector.
298 : explicit Vector(Matrix &&matrix);
299 :
300 : /// @}
301 :
302 : public:
303 : /// @name Vector size
304 : /// @{
305 :
306 : /// Resize the vector.
307 12 : void resize(size_t size) { storage.resize(size); }
308 :
309 : /// Get the number of elements in the vector.
310 40 : size_t size() const { return num_elems(); }
311 :
312 : /// Reshaping a vector to a matrix requires an explicit cast.
313 : void reshape(size_t, size_t) = delete;
314 : /// Reshaping a vector to a matrix requires an explicit cast.
315 : Matrix reshaped(size_t, size_t) = delete;
316 :
317 : /// @}
318 :
319 : public:
320 : /// @name Creating special vectors
321 : /// @{
322 :
323 : /// Create a vector filled with ones.
324 : static Vector ones(size_t size);
325 : /// Create a vector filled with zeros.
326 : static Vector zeros(size_t size);
327 : /// Create a vector filled with a constant value.
328 : static Vector constant(size_t size, double value);
329 :
330 : #ifndef NO_RANDOM_SUPPORT
331 : /// Create a vector with uniformly distributed random values.
332 : static Vector random(size_t size, double min = 0, double max = 1,
333 : std::default_random_engine::result_type seed =
334 : std::default_random_engine::default_seed);
335 : #endif
336 :
337 : /// @}
338 :
339 : public:
340 : /// @name Dot products
341 : /// @{
342 :
343 : /// Compute the dot product of two vectors. Reinterprets matrices as
344 : /// vectors.
345 : static double dot_unchecked(const Matrix &a, const Matrix &b);
346 : /// Compute the dot product of two vectors. Reinterprets matrices as
347 : /// vectors.
348 : static double dot_unchecked(Matrix &&a, const Matrix &b);
349 : /// Compute the dot product of two vectors. Reinterprets matrices as
350 : /// vectors.
351 : static double dot_unchecked(const Matrix &a, Matrix &&b);
352 : /// Compute the dot product of two vectors. Reinterprets matrices as
353 : /// vectors.
354 : static double dot_unchecked(Matrix &&a, Matrix &&b);
355 :
356 : /// Compute the dot product of two vectors.
357 : static double dot(const Vector &a, const Vector &b);
358 : /// Compute the dot product of two vectors.
359 : static double dot(Vector &&a, const Vector &b);
360 : /// Compute the dot product of two vectors.
361 : static double dot(const Vector &a, Vector &&b);
362 : /// Compute the dot product of two vectors.
363 : static double dot(Vector &&a, Vector &&b);
364 :
365 : /// Compute the dot product of this vector with another vector.
366 2 : double dot(const Vector &b) const & { return dot(*this, b); }
367 : /// Compute the dot product of this vector with another vector.
368 1 : double dot(const Vector &b) && { return dot(std::move(*this), b); }
369 : /// Compute the dot product of this vector with another vector.
370 2 : double dot(Vector &&b) const & { return dot(*this, std::move(b)); }
371 : /// Compute the dot product of this vector with another vector.
372 1 : double dot(Vector &&b) && { return dot(std::move(*this), std::move(b)); }
373 :
374 : /// @}
375 :
376 : public:
377 : /// @name Cross products
378 : /// @{
379 :
380 : /// Compute the cross product of two 3-vectors, overwriting the first vector
381 : /// with the result. Reinterprets matrices as vectors (so it can be used
382 : /// with row vectors as well).
383 : static void cross_inplace_unchecked(Matrix &a, const Matrix &b);
384 : /// Compute the opposite of the cross product of two 3-vectors, overwriting
385 : /// the first vector with the result. Reinterprets matrices as vectors
386 : /// (so it can be used with row vectors as well).
387 : static void cross_inplace_unchecked_neg(Matrix &a, const Matrix &b);
388 :
389 : /// Compute the cross product of two 3-vectors, overwriting the first vector
390 : /// with the result.
391 : static void cross_inplace(Vector &a, const Vector &b);
392 : /// Compute the cross product of two 3-vectors, overwriting the first vector
393 : /// with the result.
394 : static void cross_inplace(Vector &a, Vector &&b);
395 : /// Compute the opposite of the cross product of two 3-vectors, overwriting
396 : /// the first vector with the result.
397 : static void cross_inplace_neg(Vector &a, const Vector &b);
398 : /// Compute the opposite of the cross product of two 3-vectors, overwriting
399 : /// the first vector with the result.
400 : static void cross_inplace_neg(Vector &a, Vector &&b);
401 :
402 : /// Compute the cross product of two 3-vectors.
403 : static Vector cross(const Vector &a, const Vector &b);
404 : /// Compute the cross product of two 3-vectors.
405 : static Vector &&cross(Vector &&a, const Vector &b);
406 : /// Compute the cross product of two 3-vectors.
407 : static Vector &&cross(const Vector &a, Vector &&b);
408 : /// Compute the cross product of two 3-vectors.
409 : static Vector &&cross(Vector &&a, Vector &&b);
410 :
411 : /// Compute the cross product of this 3-vector with another 3-vector.
412 1 : Vector cross(const Vector &b) const & { return cross(*this, b); }
413 : /// Compute the cross product of this 3-vector with another 3-vector,
414 1 : Vector &&cross(const Vector &b) && { return cross(std::move(*this), b); }
415 : /// Compute the cross product of this 3-vector with another 3-vector,
416 1 : Vector &&cross(Vector &&b) const & { return cross(*this, std::move(b)); }
417 : /// Compute the cross product of this 3-vector with another 3-vector,
418 1 : Vector &&cross(Vector &&b) && {
419 1 : return cross(std::move(*this), std::move(b));
420 : }
421 :
422 : /// @}
423 :
424 : public:
425 : /// @name Vector norms
426 : /// @{
427 :
428 : /// Compute the 2-norm of the vector.
429 : double norm2() const &;
430 : /// Compute the 2-norm of the vector.
431 : double norm2() &&;
432 :
433 : /// @}
434 : };
435 :
436 : /// A row vector (1×n matrix).
437 : class RowVector : public Matrix {
438 : public:
439 : /// @name Constructors and assignment
440 : /// @{
441 :
442 : /// Default constructor.
443 : RowVector() = default;
444 :
445 : /// Create a row vector of the given size.
446 : RowVector(size_t size) : Matrix(1, size) {}
447 :
448 : /// Create a row vector from the given list of values.
449 120 : RowVector(std::initializer_list<double> init) { *this = init; }
450 :
451 : /// Assign a list of values to the column vector.
452 : RowVector &operator=(std::initializer_list<double> init);
453 :
454 : /// Convert an m×n matrix to a mn row vector.
455 : explicit RowVector(const Matrix &matrix);
456 : /// Convert an m×n matrix to a mn row vector.
457 : explicit RowVector(Matrix &&matrix);
458 :
459 : /// @}
460 :
461 : public:
462 : /// @name Vector size
463 : /// @{
464 :
465 : /// Resize the vector.
466 : void resize(size_t size) { storage.resize(size); }
467 :
468 : /// Get the number of elements in the vector.
469 : size_t size() const { return num_elems(); }
470 :
471 : /// Reshaping a vector to a matrix requires an explicit cast.
472 : void reshape(size_t, size_t) = delete;
473 : /// Reshaping a vector to a matrix requires an explicit cast.
474 : Matrix reshaped(size_t, size_t) = delete;
475 :
476 : /// @}
477 :
478 : public:
479 : /// @name Creating special row vectors
480 : /// @{
481 :
482 : /// Create a row vector filled with ones.
483 : static RowVector ones(size_t size);
484 : /// Create a row vector filled with zeros.
485 : static RowVector zeros(size_t size);
486 : /// Create a row vector filled with a constant value.
487 : static RowVector constant(size_t size, double value);
488 :
489 : #ifndef NO_RANDOM_SUPPORT
490 : /// Create a row vector with uniformly distributed random values.
491 : static RowVector random(size_t size, double min = 0, double max = 1,
492 : std::default_random_engine::result_type seed =
493 : std::default_random_engine::default_seed);
494 : #endif
495 :
496 : /// @}
497 :
498 : public:
499 : /// @name Dot products
500 : /// @{
501 :
502 : /// Compute the dot product of two vectors.
503 : static double dot(const RowVector &a, const RowVector &b);
504 : /// Compute the dot product of two vectors.
505 : static double dot(RowVector &&a, const RowVector &b);
506 : /// Compute the dot product of two vectors.
507 : static double dot(const RowVector &a, RowVector &&b);
508 : /// Compute the dot product of two vectors.
509 : static double dot(RowVector &&a, RowVector &&b);
510 :
511 : /// Compute the dot product of this vector with another vector.
512 2 : double dot(const RowVector &b) const & { return dot(*this, b); }
513 : /// Compute the dot product of this vector with another vector.
514 1 : double dot(const RowVector &b) && { return dot(std::move(*this), b); }
515 : /// Compute the dot product of this vector with another vector.
516 2 : double dot(RowVector &&b) const & { return dot(*this, std::move(b)); }
517 : /// Compute the dot product of this vector with another vector.
518 1 : double dot(RowVector &&b) && { return dot(std::move(*this), std::move(b)); }
519 :
520 : /// @}
521 :
522 : public:
523 : /// @name Cross products
524 : /// @{
525 :
526 : /// Compute the cross product of two 3-vectors, overwriting the first vector
527 : /// with the result.
528 : static void cross_inplace(RowVector &a, const RowVector &b);
529 : /// Compute the cross product of two 3-vectors, overwriting the first vector
530 : /// with the result.
531 : static void cross_inplace(RowVector &a, RowVector &&b);
532 : /// Compute the opposite of the cross product of two 3-vectors, overwriting
533 : /// the first vector with the result.
534 : static void cross_inplace_neg(RowVector &a, const RowVector &b);
535 : /// Compute the opposite of the cross product of two 3-vectors, overwriting
536 : /// the first vector with the result.
537 : static void cross_inplace_neg(RowVector &a, RowVector &&b);
538 :
539 : /// Compute the cross product of two 3-vectors.
540 : static RowVector cross(const RowVector &a, const RowVector &b);
541 : /// Compute the cross product of two 3-vectors.
542 : static RowVector &&cross(RowVector &&a, const RowVector &b);
543 : /// Compute the cross product of two 3-vectors.
544 : static RowVector &&cross(const RowVector &a, RowVector &&b);
545 : /// Compute the cross product of two 3-vectors.
546 : static RowVector &&cross(RowVector &&a, RowVector &&b);
547 :
548 : /// Compute the cross product of this 3-vector with another 3-vector.
549 : RowVector cross(const RowVector &b) const &;
550 : /// Compute the cross product of this 3-vector with another 3-vector,
551 : RowVector &&cross(const RowVector &b) &&;
552 : /// Compute the cross product of this 3-vector with another 3-vector,
553 : RowVector &&cross(RowVector &&b) const &;
554 : /// Compute the cross product of this 3-vector with another 3-vector,
555 : RowVector &&cross(RowVector &&b) &&;
556 :
557 : /// @}
558 :
559 : public:
560 : /// @name Vector norms
561 : /// @{
562 :
563 : /// Compute the 2-norm of the vector.
564 : double norm2() const &;
565 : /// Compute the 2-norm of the vector.
566 : double norm2() &&;
567 :
568 : /// @}
569 : };
570 :
571 : /// Square matrix class.
572 : class SquareMatrix : public Matrix {
573 : public:
574 : /// @name Constructors and assignment
575 : /// @{
576 :
577 : /// Default constructor.
578 26 : SquareMatrix() = default;
579 :
580 : /// Create a square matrix of zeros.
581 13 : SquareMatrix(size_t size) : Matrix(size, size) {}
582 :
583 : /// Create a square matrix with the given values.
584 : SquareMatrix(std::initializer_list<std::initializer_list<double>> init);
585 :
586 : /// Convert a general matrix to a square matrix
587 : explicit SquareMatrix(Matrix &&matrix);
588 : /// Convert a general matrix to a square matrix
589 : explicit SquareMatrix(const Matrix &matrix);
590 :
591 : /// Assign the given values to the square matrix.
592 : SquareMatrix &
593 : operator=(std::initializer_list<std::initializer_list<double>> init);
594 :
595 : /// @}
596 :
597 : public:
598 : /// @name Matrix size
599 : /// @{
600 :
601 : /// Reshaping a square matrix to a general matrix requires an explicit cast.
602 : void reshape(size_t, size_t) = delete;
603 : /// Reshaping a square matrix to a general matrix requires an explicit cast.
604 : Matrix reshaped(size_t, size_t) = delete;
605 :
606 : /// @}
607 :
608 : public:
609 : /// @name Transposition
610 : /// @{
611 :
612 : /// Transpose the matrix in-place.
613 : static void transpose_inplace(Matrix &A);
614 : /// Transpose the matrix in-place.
615 2 : void transpose_inplace() { transpose_inplace(*this); }
616 :
617 : /// @}
618 :
619 : public:
620 : /// @name Creating special matrices
621 : /// @{
622 :
623 : /// Create a square matrix filled with ones.
624 : static SquareMatrix ones(size_t rows);
625 : /// Create a square matrix filled with zeros.
626 : static SquareMatrix zeros(size_t rows);
627 : /// Create a square matrix filled with a constant value.
628 : static SquareMatrix constant(size_t rows, double value);
629 :
630 : /// Create a square identity matrix.
631 : static SquareMatrix identity(size_t rows);
632 :
633 : #ifndef NO_RANDOM_SUPPORT
634 : /// Create a matrix with uniformly distributed random values.
635 : static SquareMatrix random(size_t rows, double min = 0, double max = 1,
636 : std::default_random_engine::result_type seed =
637 : std::default_random_engine::default_seed);
638 : #endif
639 :
640 : /// @}
641 : };
642 :
643 : /// @}
644 :
645 : #ifndef NO_IOSTREAM_SUPPORT
646 : /// Print a matrix.
647 : /// @related Matrix
648 : std::ostream &operator<<(std::ostream &os, const Matrix &M);
649 : #endif
650 :
651 : #ifndef NO_ARDUINO_PRINT_SUPPORT
652 : /// Print a matrix.
653 : /// @related Matrix
654 : Print &operator<<(Print &p, const Matrix &M);
655 : #endif
656 :
657 : // :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: //
658 :
659 : /// @addtogroup MatVecOp
660 : /// @{
661 :
662 : /// @defgroup MatMul Matrix multiplication
663 : /// @brief Matrix-matrix, matrix-vector and vector-vector multiplication.
664 : /// @{
665 :
666 : /// Matrix multiplication.
667 : Matrix operator*(const Matrix &A, const Matrix &B);
668 : /// Matrix multiplication.
669 : Matrix operator*(Matrix &&A, const Matrix &B);
670 : /// Matrix multiplication.
671 : Matrix operator*(const Matrix &A, Matrix &&B);
672 : /// Matrix multiplication.
673 : Matrix operator*(Matrix &&A, Matrix &&B);
674 :
675 : /// Square matrix multiplication.
676 : SquareMatrix operator*(const SquareMatrix &A, const SquareMatrix &B);
677 : /// Square matrix multiplication.
678 : SquareMatrix operator*(SquareMatrix &&A, const SquareMatrix &B);
679 : /// Square matrix multiplication.
680 : SquareMatrix operator*(const SquareMatrix &A, SquareMatrix &&B);
681 : /// Square matrix multiplication.
682 : SquareMatrix operator*(SquareMatrix &&A, SquareMatrix &&B);
683 :
684 : /// Matrix-vector multiplication.
685 : Vector operator*(const Matrix &A, const Vector &b);
686 : /// Matrix-vector multiplication.
687 : Vector operator*(Matrix &&A, const Vector &b);
688 : /// Matrix-vector multiplication.
689 : Vector operator*(const Matrix &A, Vector &&b);
690 : /// Matrix-vector multiplication.
691 : Vector operator*(Matrix &&A, Vector &&b);
692 :
693 : /// Matrix-vector multiplication.
694 : RowVector operator*(const RowVector &a, const Matrix &B);
695 : /// Matrix-vector multiplication.
696 : RowVector operator*(RowVector &&a, const Matrix &B);
697 : /// Matrix-vector multiplication.
698 : RowVector operator*(const RowVector &a, Matrix &&B);
699 : /// Matrix-vector multiplication.
700 : RowVector operator*(RowVector &&a, Matrix &&B);
701 :
702 : /// Vector-vector multiplication.
703 : double operator*(const RowVector &a, const Vector &b);
704 : /// Vector-vector multiplication.
705 : double operator*(RowVector &&a, const Vector &b);
706 : /// Vector-vector multiplication.
707 : double operator*(const RowVector &a, Vector &&b);
708 : /// Vector-vector multiplication.
709 : double operator*(RowVector &&a, Vector &&b);
710 :
711 : /// @}
712 :
713 : // -------------------------------------------------------------------------- //
714 :
715 : /// @defgroup MatAdd Addition
716 : /// @brief Matrix and vector addition
717 : /// @{
718 :
719 : /// Matrix addition.
720 : Matrix operator+(const Matrix &A, const Matrix &B);
721 :
722 : void operator+=(Matrix &A, const Matrix &B);
723 : Matrix &&operator+(Matrix &&A, const Matrix &B);
724 : Matrix &&operator+(const Matrix &A, Matrix &&B);
725 : Matrix &&operator+(Matrix &&A, Matrix &&B);
726 : Vector &&operator+(Vector &&a, const Vector &b);
727 : Vector &&operator+(const Vector &a, Vector &&b);
728 : Vector &&operator+(Vector &&a, Vector &&b);
729 : RowVector &&operator+(RowVector &&a, const RowVector &b);
730 : RowVector &&operator+(const RowVector &a, RowVector &&b);
731 : RowVector &&operator+(RowVector &&a, RowVector &&b);
732 : SquareMatrix &&operator+(SquareMatrix &&a, const SquareMatrix &b);
733 : SquareMatrix &&operator+(const SquareMatrix &a, SquareMatrix &&b);
734 : SquareMatrix &&operator+(SquareMatrix &&a, SquareMatrix &&b);
735 : Vector operator+(const Vector &a, const Vector &b);
736 : RowVector operator+(const RowVector &a, const RowVector &b);
737 : SquareMatrix operator+(const SquareMatrix &a, const SquareMatrix &b);
738 :
739 : /// @}
740 :
741 : // -------------------------------------------------------------------------- //
742 :
743 : /// @defgroup MatSub Subtraction
744 : /// @brief Matrix and vector subtraction
745 : /// @{
746 :
747 : /// Matrix subtraction.
748 : Matrix operator-(const Matrix &A, const Matrix &B);
749 : void operator-=(Matrix &A, const Matrix &B);
750 : Matrix &&operator-(Matrix &&A, const Matrix &B);
751 : Matrix &&operator-(const Matrix &A, Matrix &&B);
752 : Matrix &&operator-(Matrix &&A, Matrix &&B);
753 : Vector &&operator-(Vector &&a, const Vector &b);
754 : Vector &&operator-(const Vector &a, Vector &&b);
755 : Vector &&operator-(Vector &&a, Vector &&b);
756 : RowVector &&operator-(RowVector &&a, const RowVector &b);
757 : RowVector &&operator-(const RowVector &a, RowVector &&b);
758 : RowVector &&operator-(RowVector &&a, RowVector &&b);
759 : SquareMatrix &&operator-(SquareMatrix &&a, const SquareMatrix &b);
760 : SquareMatrix &&operator-(const SquareMatrix &a, SquareMatrix &&b);
761 : SquareMatrix &&operator-(SquareMatrix &&a, SquareMatrix &&b);
762 : Vector operator-(const Vector &a, const Vector &b);
763 : RowVector operator-(const RowVector &a, const RowVector &b);
764 : SquareMatrix operator-(const SquareMatrix &a, const SquareMatrix &b);
765 :
766 : /// @}
767 :
768 : // -------------------------------------------------------------------------- //
769 :
770 : /// @defgroup MatNeg Negation
771 : /// @brief Matrix and vector negation
772 : /// @{
773 :
774 : /// Matrix negation.
775 : Matrix operator-(const Matrix &A);
776 : Matrix &&operator-(Matrix &&A);
777 : Vector &&operator-(Vector &&a);
778 : RowVector &&operator-(RowVector &&a);
779 : SquareMatrix &&operator-(SquareMatrix &&a);
780 : Vector operator-(const Vector &a);
781 : RowVector operator-(const RowVector &a);
782 : SquareMatrix operator-(const SquareMatrix &a);
783 :
784 : /// @}
785 :
786 : // -------------------------------------------------------------------------- //
787 :
788 : /// @defgroup ScalMul Scalar multiplication
789 : /// @brief Multiplication by a scalar
790 : /// @{
791 :
792 : /// Scalar multiplication.
793 : Matrix operator*(const Matrix &A, double s);
794 : void operator*=(Matrix &A, double s);
795 : Matrix &&operator*(Matrix &&A, double s);
796 : Vector operator*(const Vector &a, double s);
797 : RowVector operator*(const RowVector &a, double s);
798 : SquareMatrix operator*(const SquareMatrix &a, double s);
799 : Vector &&operator*(Vector &&a, double s);
800 : RowVector &&operator*(RowVector &&a, double s);
801 : SquareMatrix &&operator*(SquareMatrix &&a, double s);
802 :
803 : Matrix operator*(double s, const Matrix &A);
804 : Matrix &&operator*(double s, Matrix &&A);
805 : Vector operator*(double s, const Vector &a);
806 : RowVector operator*(double s, const RowVector &a);
807 : SquareMatrix operator*(double s, const SquareMatrix &a);
808 : Vector &&operator*(double s, Vector &&a);
809 : RowVector &&operator*(double s, RowVector &&a);
810 : SquareMatrix &&operator*(double s, SquareMatrix &&a);
811 :
812 : /// @}
813 :
814 : // -------------------------------------------------------------------------- //
815 :
816 : /// @defgroup ScalDiv Scalar division
817 : /// @brief Division by a scalar
818 : /// @{
819 :
820 : /// Scalar division.
821 : Matrix operator/(const Matrix &A, double s);
822 : void operator/=(Matrix &A, double s);
823 : Matrix &&operator/(Matrix &&A, double s);
824 : Vector operator/(const Vector &a, double s);
825 : RowVector operator/(const RowVector &a, double s);
826 : SquareMatrix operator/(const SquareMatrix &a, double s);
827 : Vector &&operator/(Vector &&a, double s);
828 : RowVector &&operator/(RowVector &&a, double s);
829 : SquareMatrix &&operator/(SquareMatrix &&a, double s);
830 :
831 : /// @}
832 :
833 : /// @}
834 :
835 : // -------------------------------------------------------------------------- //
836 :
837 : /// @addtogroup MatVecOp
838 : /// @{
839 :
840 : /// @defgroup MatTrans Transposition
841 : /// @brief Matrix and vector transposition
842 : /// @{
843 :
844 : /// Matrix transpose for general matrices.
845 : Matrix explicit_transpose(const Matrix &in);
846 :
847 : /// Matrix transpose for rectangular or square matrices and row or column
848 : /// vectors.
849 : Matrix transpose(const Matrix &in);
850 : /// Matrix transpose for rectangular or square matrices and row or column
851 : /// vectors.
852 : Matrix &&transpose(Matrix &&in);
853 :
854 : /// Square matrix transpose.
855 : SquareMatrix transpose(const SquareMatrix &in);
856 : /// Square matrix transpose.
857 : SquareMatrix &&transpose(SquareMatrix &&in);
858 :
859 : /// Vector transpose.
860 : RowVector transpose(const Vector &in);
861 : /// Vector transpose.
862 : RowVector transpose(Vector &&in);
863 : /// Vector transpose.
864 : Vector transpose(const RowVector &in);
865 : /// Vector transpose.
866 : Vector transpose(RowVector &&in);
867 :
868 : /// @}
869 :
870 : /// @}
|