PhysicsBasedAnimationToolkit 0.0.10
Cross-platform C++20 library of algorithms and data structures commonly used in computer graphics research on physically-based simulation.
Loading...
Searching...
No Matches
Inverse.h
1#ifndef PBAT_MATH_LINALG_MINI_INVERSE_H
2#define PBAT_MATH_LINALG_MINI_INVERSE_H
3
4#include "Concepts.h"
5#include "Matrix.h"
6#include "pbat/HostDevice.h"
7
8#include <type_traits>
9#include <utility>
10
11namespace pbat {
12namespace math {
13namespace linalg {
14namespace mini {
15
16template <class /*CMatrix*/ TMatrix>
17PBAT_HOST_DEVICE SMatrix<
18 typename std::remove_cvref_t<TMatrix>::ScalarType,
19 std::remove_cvref_t<TMatrix>::kRows,
20 std::remove_cvref_t<TMatrix>::kCols>
21Inverse(TMatrix&& A)
22{
23 using InputMatrixType = std::remove_cvref_t<TMatrix>;
24 PBAT_MINI_CHECK_CMATRIX(InputMatrixType);
25 static_assert(
26 InputMatrixType::kRows < 4 and InputMatrixType::kRows > 1,
27 "Cannot compute inverse of large matrix or scalar");
28 static_assert(
29 InputMatrixType::kRows == InputMatrixType::kCols,
30 "Cannot compute inverse of non-square matrix");
31 using ScalarType = typename InputMatrixType::ScalarType;
33 MatrixType Ainv{};
34 if constexpr (MatrixType::kRows == 2)
35 {
36 auto const a0 = ScalarType(1.0) / (A(0, 0) * A(1, 1) - A(1, 0) * A(0, 1));
37 Ainv(0, 0) = a0 * A(1, 1);
38 Ainv(1, 0) = -a0 * A(1, 0);
39 Ainv(0, 1) = -a0 * A(0, 1);
40 Ainv(1, 1) = a0 * A(0, 0);
41 }
42 if constexpr (MatrixType::kRows == 3)
43 {
44 auto const a0 = A(1, 1) * A(2, 2);
45 auto const a1 = A(2, 1) * A(1, 2);
46 auto const a2 = A(1, 0) * A(2, 1);
47 auto const a3 = A(1, 0) * A(2, 2);
48 auto const a4 = A(2, 0) * A(1, 1);
49 auto const a5 =
50 ScalarType(1.0) / (a0 * A(0, 0) - a1 * A(0, 0) + a2 * A(0, 2) - a3 * A(0, 1) -
51 a4 * A(0, 2) + A(2, 0) * A(0, 1) * A(1, 2));
52 Ainv(0, 0) = a5 * (a0 - a1);
53 Ainv(1, 0) = a5 * (-a3 + A(2, 0) * A(1, 2));
54 Ainv(2, 0) = a5 * (a2 - a4);
55 Ainv(0, 1) = a5 * (-A(0, 1) * A(2, 2) + A(2, 1) * A(0, 2));
56 Ainv(1, 1) = a5 * (A(0, 0) * A(2, 2) - A(2, 0) * A(0, 2));
57 Ainv(2, 1) = a5 * (-A(0, 0) * A(2, 1) + A(2, 0) * A(0, 1));
58 Ainv(0, 2) = a5 * (A(0, 1) * A(1, 2) - A(1, 1) * A(0, 2));
59 Ainv(1, 2) = a5 * (-A(0, 0) * A(1, 2) + A(1, 0) * A(0, 2));
60 Ainv(2, 2) = a5 * (A(0, 0) * A(1, 1) - A(1, 0) * A(0, 1));
61 }
62 return Ainv;
63}
64
65} // namespace mini
66} // namespace linalg
67} // namespace math
68} // namespace pbat
69
70#endif // PBAT_MATH_LINALG_MINI_INVERSE_H
Definition Matrix.h:121
Mini linear algebra related functionality.
Definition Assign.h:12
Linear Algebra related functionality.
Definition FilterEigenvalues.h:7
Math related functionality.
Definition Concepts.h:19
The main namespace of the library.
Definition Aliases.h:15