<T>LAPACK 0.1.1
C++ Template Linear Algebra PACKage
Loading...
Searching...
No Matches
larft.hpp
Go to the documentation of this file.
1
5//
6// Copyright (c) 2021-2023, University of Colorado Denver. All rights reserved.
7//
8// This file is part of <T>LAPACK.
9// <T>LAPACK is free software: you can redistribute it and/or modify it under
10// the terms of the BSD 3-Clause license. See the accompanying LICENSE file.
11
12#ifndef TLAPACK_LARFT_HH
13#define TLAPACK_LARFT_HH
14
16#include "tlapack/blas/gemm.hpp"
17#include "tlapack/blas/gemv.hpp"
18#include "tlapack/blas/trmv.hpp"
19
20namespace tlapack {
21
87template <TLAPACK_DIRECTION direction_t,
88 TLAPACK_STOREV storage_t,
89 TLAPACK_SMATRIX matrixV_t,
90 TLAPACK_VECTOR vector_t,
91 TLAPACK_SMATRIX matrixT_t>
92int larft(direction_t direction,
94 const matrixV_t& V,
95 const vector_t& tau,
96 matrixT_t& T)
97{
98 // data traits
101 using tau_t = type_t<vector_t>;
102 using idx_t = size_type<matrixV_t>;
103
104 // using
106
107 // constants
108 const real_t one(1);
109 const real_t zero(0);
110 const idx_t n = (storeMode == StoreV::Columnwise) ? nrows(V) : ncols(V);
111 const idx_t k = size(tau);
112
113 // check arguments
114 tlapack_check_false(direction != Direction::Backward &&
115 direction != Direction::Forward);
116 tlapack_check_false(storeMode != StoreV::Columnwise &&
117 storeMode != StoreV::Rowwise);
119 k > ((storeMode == StoreV::Columnwise) ? ncols(V) : nrows(V)));
120 tlapack_check_false(nrows(T) < k || ncols(T) < k);
121
122 // Quick return
123 if (n == 0 || k == 0) return 0;
124
125 if (direction == Direction::Forward) {
126 // First iteration:
127 T(0, 0) = tau[0];
128
129 // Remaining iterations:
130 for (idx_t i = 1; i < k; ++i) {
131 // Column vector t := T(0:i,i)
132 auto t = slice(T, range{0, i}, i);
133
134 if (tau[i] == tau_t(0)) {
135 // H(i) = I
136 for (idx_t j = 0; j < i; ++j)
137 t[j] = zero;
138 }
139
140 else {
141 // General case
142 if (storeMode == StoreV::Columnwise) {
143 // t := - tau[i] conj( V(i,0:i) )
144 for (idx_t j = 0; j < i; ++j)
145 t[j] = -tau[i] * conj(V(i, j));
146
147 // t := t - tau[i] V(i+1:n,0:i)^H V(i+1:n,i)
148 if (i + 1 < n) {
149 gemv(CONJ_TRANS, -tau[i],
150 slice(V, range{i + 1, n}, range{0, i}),
151 slice(V, range{i + 1, n}, i), one, t);
152 }
153 }
154 else {
155 // t := - tau[i] V(0:i,i)
156 for (idx_t j = 0; j < i; ++j)
157 t[j] = -tau[i] * V(j, i);
158
159 // t := t - tau[i] V(0:i,i:n) V(i,i+1:n)^H
160 if (i + 1 < n) {
161 auto Ti = slice(T, range{0, i}, range{i, i + 1});
163 slice(V, range{0, i}, range{i + 1, n}),
164 slice(V, range{i, i + 1}, range{i + 1, n}), one,
165 Ti);
166 }
167 }
168
169 // t := T(0:i,0:i) * t
171 slice(T, range{0, i}, range{0, i}), t);
172 }
173
174 // Update diagonal
175 T(i, i) = tau[i];
176 }
177 }
178 else // direct==Direction::Backward
179 {
180 // First iteration:
181 T(k - 1, k - 1) = tau[k - 1];
182
183 // Remaining iterations:
184 for (idx_t i = k - 2; i != idx_t(-1); --i) {
185 // Column vector t := T(0:i,i)
186 auto t = slice(T, range{i + 1, k}, i);
187
188 if (tau[i] == tau_t(0)) {
189 // H(i) = I
190 for (idx_t j = 0; j < k - i - 1; ++j)
191 t[j] = zero;
192 }
193
194 else {
195 // General case
196 if (storeMode == StoreV::Columnwise) {
197 // t := - tau[i] conj(V(n-k+i,i+1:k))
198 for (idx_t j = 0; j < k - i - 1; ++j)
199 t[j] = -tau[i] * conj(V(n - k + i, j + i + 1));
200
201 // t := t - tau[i] V(0:n-k+i,i+1:k)^H V(0:n-k+i,i)
202 gemv(CONJ_TRANS, -tau[i],
203 slice(V, range{0, n - k + i}, range{i + 1, k}),
204 slice(V, range{0, n - k + i}, i), one, t);
205 }
206 else {
207 // t := - tau[i] V(i+1:k,n-k+i)
208 for (idx_t j = 0; j < k - i - 1; ++j)
209 t[j] = -tau[i] * V(j + i + 1, n - k + i);
210
211 // t := t - tau[i] V(i+1:k,0:n-k+i) V(i,0:n-k+i)^H
212 auto Ti = slice(T, range{i + 1, k}, range{i, i + 1});
214 slice(V, range{i + 1, k}, range{0, n - k + i}),
215 slice(V, range{i, i + 1}, range{0, n - k + i}), one,
216 Ti);
217 }
218
219 // t := T(i+1:k,i+1:k) * t
221 slice(T, range{i + 1, k}, range{i + 1, k}), t);
222 }
223
224 // Update diagonal
225 T(i, i) = tau[i];
226 }
227 }
228 return 0;
229}
230
231} // namespace tlapack
232
233#endif // TLAPACK_LARFT_HH
constexpr internal::LowerTriangle LOWER_TRIANGLE
Lower Triangle access.
Definition types.hpp:183
constexpr internal::UpperTriangle UPPER_TRIANGLE
Upper Triangle access.
Definition types.hpp:181
constexpr internal::NonUnitDiagonal NON_UNIT_DIAG
The main diagonal is not assumed to consist of 1's.
Definition types.hpp:215
constexpr internal::ConjTranspose CONJ_TRANS
conjugate transpose
Definition types.hpp:259
constexpr internal::NoTranspose NO_TRANS
no transpose
Definition types.hpp:255
constexpr T conj(const T &x) noexcept
Extends std::conj() to real datatypes.
Definition utils.hpp:100
#define TLAPACK_STOREV
Macro for tlapack::concepts::StoreV compatible with C++17.
Definition concepts.hpp:936
#define TLAPACK_SMATRIX
Macro for tlapack::concepts::SliceableMatrix compatible with C++17.
Definition concepts.hpp:899
#define TLAPACK_DIRECTION
Macro for tlapack::concepts::Direction compatible with C++17.
Definition concepts.hpp:930
#define TLAPACK_VECTOR
Macro for tlapack::concepts::Vector compatible with C++17.
Definition concepts.hpp:906
int larft(direction_t direction, storage_t storeMode, const matrixV_t &V, const vector_t &tau, matrixT_t &T)
Forms the triangular factor T of a block reflector H of order n, which is defined as a product of k e...
Definition larft.hpp:92
void gemv(Op trans, const alpha_t &alpha, const matrixA_t &A, const vectorX_t &x, const beta_t &beta, vectorY_t &y)
General matrix-vector multiply:
Definition gemv.hpp:57
void trmv(Uplo uplo, Op trans, Diag diag, const matrixA_t &A, vectorX_t &x)
Triangular matrix-vector multiply:
Definition trmv.hpp:60
void gemm(Op transA, Op transB, const alpha_t &alpha, const matrixA_t &A, const matrixB_t &B, const beta_t &beta, matrixC_t &C)
General matrix-matrix multiply:
Definition gemm.hpp:61
#define tlapack_check_false(cond)
Throw an error if cond is true.
Definition exceptionHandling.hpp:113
typename traits::real_type_traits< Types..., int >::type real_type
The common real type of the list of types.
Definition scalar_type_traits.hpp:113