Expression Templates Library (ETL)
decomposition.hpp
Go to the documentation of this file.
1 //=======================================================================
2 // Copyright (c) 2014-2023 Baptiste Wicht
3 // Distributed under the terms of the MIT License.
4 // (See accompanying file LICENSE or copy at
5 // http://opensource.org/licenses/MIT)
6 //=======================================================================
7 
13 #pragma once
14 
15 namespace etl::impl::standard {
16 
24 template <typename AT, typename LT, typename UT, typename PT>
25 void lu(const AT& A, LT& L, UT& U, PT& P) {
26  const auto n = etl::dim(A, 0);
27 
28  L = 0;
29  U = 0;
30  P = 0;
31 
32  // 1. Create the pivot matrix
33 
34  for (size_t i = 0; i < n; ++i) {
35  P(i, i) = 1;
36  }
37 
38  for (size_t i = 0; i < n; ++i) {
39  auto max_j = i;
40 
41  for (size_t j = i; j < n; ++j) {
42  if (std::abs(A(j, i)) > A(max_j, i)) {
43  max_j = j;
44  }
45  }
46 
47  if (max_j != i) {
48  for (size_t k = 0; k < n; ++k) {
49  using std::swap;
50  swap(P(i, k), P(max_j, k));
51  }
52  }
53  }
54 
55  auto Ap = etl::force_temporary(P * A);
56 
57  for (size_t i = 0; i < n; ++i) {
58  L(i, i) = 1;
59  }
60 
61  for (size_t i = 0; i < n; ++i) {
62  for (size_t j = 0; j < n; ++j) {
63  if (j <= i) {
64  value_t<AT> s = 0;
65  for (size_t k = 0; k < j; ++k) {
66  s += L(j, k) * U(k, i);
67  }
68 
69  U(j, i) = Ap(j, i) - s;
70  }
71 
72  if (j >= i) {
73  value_t<AT> s = 0;
74  for (size_t k = 0; k < i; ++k) {
75  s += L(j, k) * U(k, i);
76  }
77 
78  L(j, i) = (Ap(j, i) - s) / U(i, i);
79  }
80  }
81  }
82 }
83 
90 template <typename AT, typename QT, typename RT>
91 void householder(AT& A, QT& Q, RT& R) {
92  using T = value_t<AT>;
93 
94  const auto m = etl::dim<0>(A);
95  const auto n = etl::dim<1>(A);
96 
97  std::vector<etl::dyn_matrix<T, 2>> q;
98  q.reserve(m);
99 
100  for (size_t i = 0; i < m; ++i) {
101  q.emplace_back(m, m);
102  }
103 
104  etl::dyn_matrix<T> z(m, n);
105  z = A;
106 
107  for (size_t k = 0; k < n && k < m - 1; k++) {
108  etl::dyn_matrix<T> zz(m, n, T(0));
109 
110  for (size_t i = 0; i < k; ++i) {
111  zz(i, i) = 1;
112  }
113 
114  for (size_t i = k; i < m; ++i) {
115  for (size_t j = k; j < n; ++j) {
116  zz(i, j) = z(i, j);
117  }
118  }
119 
120  z = std::move(zz);
121 
122  // x -> Take k-th column of z
123  etl::dyn_vector<T> x(m);
124 
125  for (size_t i = 0; i < m; ++i) {
126  x[i] = z(i, k);
127  }
128 
129  auto a = norm(x);
130  if (A(k, k) > 0) {
131  a = -a;
132  }
133 
134  x[k] += a;
135 
136  x /= norm(x);
137 
138  for (size_t i = 0; i < m; ++i) {
139  for (size_t j = 0; j < m; ++j) {
140  q[k](i, j) = T(-2) * x[i] * x[j];
141  }
142 
143  q[k](i, i) += 1;
144  }
145 
146  z = q[k] * z;
147  }
148 
149  Q = q[0];
150 
151  for (size_t i = 1; i < n && i < m - 1; i++) {
152  Q = q[i] * Q;
153  }
154 
155  R = Q * A;
156 
157  Q = transpose(Q);
158 }
159 
166 template <typename AT, typename QT, typename RT>
167 void qr(AT& A, QT& Q, RT& R) {
168  householder(A, Q, R);
169 }
170 
171 } //end of namespace etl::impl::standard
auto s(T &&value)
Force the evaluation of the given expression.
Definition: stop.hpp:18
bool qr(AT &A, QT &Q, RT &R)
Decomposition the matrix so that A = Q * R.
Definition: globals.hpp:332
Definition: prob_pooling.hpp:10
auto abs(E &&value)
Apply absolute on each value of the given expression.
Definition: expression_builder.hpp:54
auto transpose(const E &value)
Returns the transpose of the given expression.
Definition: expression_builder.hpp:528
auto dim(E &&value, size_t i) -> detail::identity_helper< E, dim_view< detail::build_identity_type< E >, D >>
Return a view representing the ith Dth dimension.
Definition: view_expression_builder.hpp:25
bool lu(const AT &A, LT &L, UT &U, PT &P)
Decomposition the matrix so that P * A = L * U.
Definition: globals.hpp:308
Matrix with run-time fixed dimensions.
Definition: dyn.hpp:26
void swap(custom_dyn_matrix_impl< T, SO, D > &lhs, custom_dyn_matrix_impl< T, SO, D > &rhs)
Swap two dyn matrix.
Definition: custom_dyn.hpp:403
void householder(AT &A, QT &Q, RT &R)
Use the householder algorithm to perform the A=QR decomposition of the matrix A.
Definition: decomposition.hpp:91
decltype(auto) force_temporary(E &&expr)
Force a temporary out of the expression.
Definition: temporary.hpp:91
typename decay_traits< E >::value_type value_t
Traits to extract the value type out of an ETL type.
Definition: tmp.hpp:81
value_t< A > norm(const A &a)
Returns euclidean norm of the given expression.
Definition: expression_builder.hpp:578