12#ifndef ARCCORE_ALINA_DENSEMATRIXINVERSEIMPL_H
13#define ARCCORE_ALINA_DENSEMATRIXINVERSEIMPL_H
29#include "arccore/alina/AlinaUtils.h"
30#include "arccore/alina/ValueTypeInterface.h"
35namespace Arcane::Alina::detail
43template <
typename value_type>
static void
44inverse(
int n, value_type* A, value_type* t,
int* p)
46 std::iota(p, p + n, 0);
49 for (
int col = 0; col < n; ++col) {
52 using mag_type =
typename math::scalar_of<value_type>::type;
53 mag_type pivot_mag = math::zero<mag_type>();
54 for (
int i = col; i < n; ++i) {
56 mag_type mag = math::norm(A[row * n + col]);
57 if (mag > pivot_mag) {
62 std::swap(p[col], p[pivot_i]);
63 int pivot_row = p[col];
65 value_type d = math::inverse(A[pivot_row * n + col]);
66 assert(!math::is_zero(d));
67 for (
int i = col + 1; i < n; ++i) {
69 A[row * n + col] *= d;
70 for (
int j = col + 1; j < n; ++j)
71 A[row * n + j] -= A[row * n + col] * A[pivot_row * n + j];
73 A[pivot_row * n + col] = d;
77 for (
int k = 0; k < n; ++k) {
79 for (
int i = 0; i < n; ++i) {
81 value_type b = (row == k) ? math::identity<value_type>() : math::zero<value_type>();
82 for (
int j = 0; j < i; ++j)
83 b -= A[row * n + j] * t[j * n + k];
88 for (
int i = n; i-- > 0;) {
90 for (
int j = i + 1; j < n; ++j)
91 t[i * n + k] -= A[row * n + j] * t[j * n + k];
92 t[i * n + k] *= A[row * n + i];
96 std::copy(t, t + n * n, A);